mirror of
https://gitlab.freedesktop.org/cairo/cairo.git
synced 2026-05-05 06:28:01 +02:00
[fix] Avoid int overflow when allocating large buffers
This patch introduces three macros: _cairo_malloc_ab, _cairo_malloc_abc, _cairo_malloc_ab_plus_c and replaces various calls to malloc(a*b), malloc(a*b*c), and malloc(a*b+c) with them. The macros return NULL if int overflow would occur during the allocation. See CODING_STYLE for more information.
This commit is contained in:
parent
fc34073464
commit
5c7d2d14d7
41 changed files with 308 additions and 89 deletions
25
CODING_STYLE
25
CODING_STYLE
|
|
@ -243,3 +243,28 @@ The return statement is often the best thing to use in a pattern like
|
|||
this. If it's not available due to additional nesting above which
|
||||
require some cleanup after the current block, then consider splitting
|
||||
the current block into a new function before using goto.
|
||||
|
||||
Memory allocation
|
||||
-----------------
|
||||
|
||||
Because much of cairo's data consists of dynamically allocated arrays,
|
||||
it's very easy to introduce integer overflow issues whenever malloc()
|
||||
is called. Use the _cairo_malloc2(), _cairo_malloc3(), and
|
||||
_cairo_malloc2_add1 macros to avoid these cases; these macros check
|
||||
for overflow and will return NULL in that case.
|
||||
|
||||
malloc (n * size) => _cairo_malloc_ab (n, size)
|
||||
e.g. malloc (num_elts * sizeof(some_type)) =>
|
||||
_cairo_malloc2 (num_elts, sizeof(some_type))
|
||||
|
||||
malloc (a * b * size) => _cairo_malloc_abc (a, b, size)
|
||||
e.g. malloc (width * height * 4) =>
|
||||
_cairo_malloc3 (width, height, 4)
|
||||
|
||||
malloc (n * size + k) => _cairo_malloc_ab_plus_c (n, size, k)
|
||||
e.g. malloc (num * sizeof(entry) + sizeof(header)) =>
|
||||
_cairo_malloc2k (num, sizeof(entry), sizeof(header))
|
||||
|
||||
In general, be wary of performing any arithmetic operations in an
|
||||
argument to malloc. You should explicitly check for integer overflow
|
||||
yourself in any more complex situations.
|
||||
|
|
@ -3883,7 +3883,7 @@ static void fbFetchExternalAlpha(PicturePtr pict, int x, int y, int width, CARD3
|
|||
}
|
||||
|
||||
if (width > SCANLINE_BUFFER_LENGTH)
|
||||
alpha_buffer = (CARD32 *) malloc(width*sizeof(CARD32));
|
||||
alpha_buffer = (CARD32 *) _pixman_malloc_ab (width, sizeof(CARD32));
|
||||
|
||||
fbFetchTransformed(pict, x, y, width, buffer, mask, maskBits);
|
||||
fbFetchTransformed(pict->alphaMap, x - pict->alphaOrigin.x,
|
||||
|
|
@ -4286,7 +4286,7 @@ pixman_compositeGeneral (pixman_operator_t op,
|
|||
compose_data.mask = pMask;
|
||||
compose_data.dest = pDst;
|
||||
if (width > SCANLINE_BUFFER_LENGTH)
|
||||
scanline_buffer = (CARD32 *) malloc(width * 3 * sizeof(CARD32));
|
||||
scanline_buffer = (CARD32 *) _pixman_malloc_abc (width, 3, sizeof(CARD32));
|
||||
|
||||
n = pixman_region_num_rects (®ion);
|
||||
pbox = pixman_region_rects (®ion);
|
||||
|
|
|
|||
|
|
@ -215,8 +215,8 @@ pixman_image_create_linear_gradient (const pixman_linear_gradient_t *gradient,
|
|||
if (!image)
|
||||
return NULL;
|
||||
|
||||
linear = malloc (sizeof (pixman_linear_gradient_image_t) +
|
||||
sizeof (pixman_gradient_stop_t) * n_stops);
|
||||
linear = _pixman_malloc_ab_plus_c (n_stops, sizeof (pixman_gradient_stop_t),
|
||||
sizeof (pixman_linear_gradient_image_t));
|
||||
if (!linear)
|
||||
{
|
||||
free (image);
|
||||
|
|
@ -259,8 +259,8 @@ pixman_image_create_radial_gradient (const pixman_radial_gradient_t *gradient,
|
|||
if (!image)
|
||||
return NULL;
|
||||
|
||||
radial = malloc (sizeof (pixman_radial_gradient_image_t) +
|
||||
sizeof (pixman_gradient_stop_t) * n_stops);
|
||||
radial = _pixman_malloc_ab_plus_c (n_stops, sizeof (pixman_gradient_stop_t),
|
||||
sizeof (pixman_radial_gradient_image_t));
|
||||
if (!radial)
|
||||
{
|
||||
free (image);
|
||||
|
|
|
|||
|
|
@ -89,6 +89,13 @@ SOFTWARE.
|
|||
typedef unsigned __int32 uint32_t;
|
||||
typedef __int64 int64_t;
|
||||
typedef unsigned __int64 uint64_t;
|
||||
|
||||
# ifndef UINT16_MAX
|
||||
# define UINT16_MAX (65535)
|
||||
# endif
|
||||
# ifndef UINT32_MAX
|
||||
# define UINT32_MAX (0xffffffffU)
|
||||
# endif
|
||||
#else
|
||||
#error Cannot find definitions for fixed-width integral types (uint8_t, uint32_t, etc.)
|
||||
#endif
|
||||
|
|
|
|||
|
|
@ -1073,4 +1073,21 @@ typedef xFixed_16_16 xFixed;
|
|||
(*((a)+2) = (CARD8) ((v) >> 16))))
|
||||
#endif
|
||||
|
||||
|
||||
/* Allocation helpers */
|
||||
|
||||
#define _pixman_malloc_ab(n, size) \
|
||||
((unsigned) (n) >= INT32_MAX / (unsigned) (size) ? NULL : \
|
||||
malloc((unsigned) (n) * (unsigned) (size)))
|
||||
|
||||
#define _pixman_malloc_abc(a, b, size) \
|
||||
((unsigned) (a) >= INT32_MAX / (unsigned) (b) ? NULL : \
|
||||
(unsigned) ((a)*(b)) >= INT32_MAX / (unsigned) (size) ? NULL : \
|
||||
malloc((unsigned) (a) * (unsigned) (b) * (unsigned) size))
|
||||
|
||||
#define _pixman_malloc_ab_plus_c(n, size, k) \
|
||||
((unsigned) (n) >= INT32_MAX / (unsigned) (size) ? NULL : \
|
||||
(unsigned) (k) >= INT32_MAX - (unsigned) (n) * (unsigned) (size) ? NULL : \
|
||||
malloc((unsigned) (n) * (unsigned) (size) + (unsigned) (k)))
|
||||
|
||||
#endif /* _PIXMANINT_H_ */
|
||||
|
|
|
|||
|
|
@ -148,7 +148,31 @@ pixman_rect_alloc(pixman_region16_t * region, int n);
|
|||
((r1)->y1 <= (r2)->y1) && \
|
||||
((r1)->y2 >= (r2)->y2) )
|
||||
|
||||
#define allocData(n) malloc(PIXREGION_SZOF(n))
|
||||
static size_t
|
||||
PIXREGION_SZOF(size_t n)
|
||||
{
|
||||
size_t size = n * sizeof(pixman_box16_t);
|
||||
if (n > UINT32_MAX / sizeof(pixman_box16_t))
|
||||
return 0;
|
||||
|
||||
if (sizeof(pixman_region16_data_t) > UINT32_MAX - size)
|
||||
return 0;
|
||||
|
||||
return size + sizeof(pixman_region16_data_t);
|
||||
}
|
||||
|
||||
static void
|
||||
allocData(size_t n, void **data)
|
||||
{
|
||||
size_t sz = PIXREGION_SZOF(n);
|
||||
if (!sz) {
|
||||
*data = NULL;
|
||||
return;
|
||||
}
|
||||
|
||||
*data = malloc(sz);
|
||||
}
|
||||
|
||||
#define freeData(reg) if ((reg)->data && (reg)->data->size) free((reg)->data)
|
||||
|
||||
#define RECTALLOC_BAIL(pReg,n,bail) \
|
||||
|
|
@ -185,7 +209,10 @@ if (!(pReg)->data || (((pReg)->data->numRects + (n)) > (pReg)->data->size)) \
|
|||
if (((numRects) < ((reg)->data->size >> 1)) && ((reg)->data->size > 50)) \
|
||||
{ \
|
||||
pixman_region16_data_t * NewData; \
|
||||
NewData = (pixman_region16_data_t *)realloc((reg)->data, PIXREGION_SZOF(numRects)); \
|
||||
size_t data_size = PIXREGION_SZOF(numRects); \
|
||||
if (!data_size) \
|
||||
goto bail; \
|
||||
NewData = (pixman_region16_data_t *)realloc((reg)->data, data_size); \
|
||||
if (NewData) \
|
||||
{ \
|
||||
NewData->size = (numRects); \
|
||||
|
|
@ -372,11 +399,12 @@ static pixman_region_status_t
|
|||
pixman_rect_alloc(pixman_region16_t * region, int n)
|
||||
{
|
||||
pixman_region16_data_t *data;
|
||||
size_t data_size;
|
||||
|
||||
if (!region->data)
|
||||
{
|
||||
n++;
|
||||
region->data = allocData(n);
|
||||
allocData(n, (void **) ®ion->data);
|
||||
if (!region->data)
|
||||
return pixman_break (region);
|
||||
region->data->numRects = 1;
|
||||
|
|
@ -384,7 +412,7 @@ pixman_rect_alloc(pixman_region16_t * region, int n)
|
|||
}
|
||||
else if (!region->data->size)
|
||||
{
|
||||
region->data = allocData(n);
|
||||
allocData(n, (void **) ®ion->data);
|
||||
if (!region->data)
|
||||
return pixman_break (region);
|
||||
region->data->numRects = 0;
|
||||
|
|
@ -398,7 +426,10 @@ pixman_rect_alloc(pixman_region16_t * region, int n)
|
|||
n = 250;
|
||||
}
|
||||
n += region->data->numRects;
|
||||
data = (pixman_region16_data_t *)realloc(region->data, PIXREGION_SZOF(n));
|
||||
data_size = PIXREGION_SZOF(n);
|
||||
if (!data_size)
|
||||
return pixman_break (region);
|
||||
data = (pixman_region16_data_t *)realloc(region->data, data_size);
|
||||
if (!data)
|
||||
return pixman_break (region);
|
||||
region->data = data;
|
||||
|
|
@ -424,7 +455,7 @@ pixman_region_copy(pixman_region16_t *dst, pixman_region16_t *src)
|
|||
if (!dst->data || (dst->data->size < src->data->numRects))
|
||||
{
|
||||
freeData(dst);
|
||||
dst->data = allocData(src->data->numRects);
|
||||
allocData(src->data->numRects, (void **) &dst->data);
|
||||
if (!dst->data)
|
||||
return pixman_break (dst);
|
||||
dst->data->size = src->data->numRects;
|
||||
|
|
@ -835,8 +866,10 @@ pixman_op(
|
|||
AppendRegions(newReg, r2BandEnd, r2End);
|
||||
}
|
||||
|
||||
if (oldData)
|
||||
if (oldData) {
|
||||
free(oldData);
|
||||
oldData = NULL;
|
||||
}
|
||||
|
||||
if (!(numRects = newReg->data->numRects))
|
||||
{
|
||||
|
|
@ -1493,7 +1526,7 @@ pixman_region_validate(pixman_region16_t * badreg,
|
|||
|
||||
/* Set up the first region to be the first rectangle in badreg */
|
||||
/* Note that step 2 code will never overflow the ri[0].reg rects array */
|
||||
ri = (RegionInfo *) malloc(4 * sizeof(RegionInfo));
|
||||
ri = (RegionInfo *) _pixman_malloc_ab(4, sizeof(RegionInfo));
|
||||
if (!ri)
|
||||
return pixman_break (badreg);
|
||||
sizeRI = 4;
|
||||
|
|
@ -1555,9 +1588,13 @@ pixman_region_validate(pixman_region16_t * badreg,
|
|||
/* Uh-oh. No regions were appropriate. Create a new one. */
|
||||
if (sizeRI == numRI)
|
||||
{
|
||||
size_t data_size;
|
||||
/* Oops, allocate space for new region information */
|
||||
sizeRI <<= 1;
|
||||
rit = (RegionInfo *) realloc(ri, sizeRI * sizeof(RegionInfo));
|
||||
data_size = sizeRI * sizeof(RegionInfo);
|
||||
if (data_size / sizeRI != sizeof(RegionInfo))
|
||||
goto bail;
|
||||
rit = (RegionInfo *) realloc(ri, data_size);
|
||||
if (!rit)
|
||||
goto bail;
|
||||
ri = rit;
|
||||
|
|
@ -1659,7 +1696,7 @@ pixman_region_rectsToRegion(nrects, prect, ctype)
|
|||
}
|
||||
return region;
|
||||
}
|
||||
pData = allocData(nrects);
|
||||
allocData(nrects, &pData);
|
||||
if (!pData)
|
||||
{
|
||||
pixman_break (region);
|
||||
|
|
@ -2167,7 +2204,7 @@ pixman_region16_data_copy(pixman_region16_t * dst, pixman_region16_t * src)
|
|||
if (!dst->data || (dst->data->size < src->data->numRects))
|
||||
{
|
||||
freeData(dst);
|
||||
dst->data = allocData(src->data->numRects);
|
||||
allocData(src->data->numRects, &dst->data);
|
||||
if (!dst->data)
|
||||
return pixman_break (dst);
|
||||
}
|
||||
|
|
|
|||
|
|
@ -70,6 +70,5 @@ typedef struct pixman_region16_point {
|
|||
#define PIXREGION_BOX(reg,i) (&PIXREGION_BOXPTR(reg)[i])
|
||||
#define PIXREGION_TOP(reg) PIXREGION_BOX(reg, (reg)->data->numRects)
|
||||
#define PIXREGION_END(reg) PIXREGION_BOX(reg, (reg)->data->numRects - 1)
|
||||
#define PIXREGION_SZOF(n) (sizeof(pixman_region16_data_t) + ((n) * sizeof(pixman_box16_t)))
|
||||
|
||||
#endif /* _PIXREGIONINT_H_ */
|
||||
|
|
|
|||
|
|
@ -809,7 +809,7 @@ _cairo_atsui_font_text_to_glyphs (void *abstract_font,
|
|||
|
||||
*num_glyphs = glyphCount - 1;
|
||||
*glyphs =
|
||||
(cairo_glyph_t *) malloc(*num_glyphs * (sizeof (cairo_glyph_t)));
|
||||
(cairo_glyph_t *) _cairo_malloc_ab(*num_glyphs, sizeof (cairo_glyph_t));
|
||||
if (*glyphs == NULL) {
|
||||
return CAIRO_STATUS_NO_MEMORY;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -754,7 +754,7 @@ _cairo_bo_event_queue_init (cairo_bo_event_queue_t *event_queue,
|
|||
* or stop events, so this allocation is safe. XXX: make the
|
||||
* event type a union so it doesn't always contain the skip
|
||||
* elt? */
|
||||
events = malloc (num_events * (sizeof (cairo_bo_event_t) + sizeof(cairo_bo_event_t*)));
|
||||
events = _cairo_malloc_ab (num_events, sizeof (cairo_bo_event_t) + sizeof(cairo_bo_event_t*));
|
||||
if (events == NULL)
|
||||
return CAIRO_STATUS_NO_MEMORY;
|
||||
|
||||
|
|
@ -1436,7 +1436,7 @@ _cairo_bentley_ottmann_tessellate_polygon (cairo_traps_t *traps,
|
|||
if (polygon->num_edges < ARRAY_LENGTH (stack_edges)) {
|
||||
edges = stack_edges;
|
||||
} else {
|
||||
edges = malloc (polygon->num_edges * sizeof (cairo_bo_edge_t));
|
||||
edges = _cairo_malloc_ab (polygon->num_edges, sizeof (cairo_bo_edge_t));
|
||||
if (edges == NULL)
|
||||
return CAIRO_STATUS_NO_MEMORY;
|
||||
}
|
||||
|
|
@ -1757,7 +1757,7 @@ run_test (const char *test_name,
|
|||
while (intersections) {
|
||||
int num_edges = _cairo_array_num_elements (&intersected_edges);
|
||||
passes++;
|
||||
edges = malloc (num_edges * sizeof (cairo_bo_edge_t));
|
||||
edges = _cairo_malloc_ab (num_edges, sizeof (cairo_bo_edge_t));
|
||||
assert (edges != NULL);
|
||||
memcpy (edges, _cairo_array_index (&intersected_edges, 0), num_edges * sizeof (cairo_bo_edge_t));
|
||||
_cairo_array_fini (&intersected_edges);
|
||||
|
|
|
|||
|
|
@ -259,7 +259,7 @@ premultiply_rgba (unsigned char* data,
|
|||
int height,
|
||||
int stride)
|
||||
{
|
||||
unsigned char* retdata = reinterpret_cast<unsigned char*>(malloc(stride * height));
|
||||
unsigned char* retdata = reinterpret_cast<unsigned char*>(_cairo_malloc_ab(height, stride));
|
||||
if (!retdata)
|
||||
return NULL;
|
||||
|
||||
|
|
@ -322,7 +322,7 @@ _cairo_beos_bitmap_to_surface (BBitmap* bitmap)
|
|||
bitmap->BytesPerRow());
|
||||
} else {
|
||||
premultiplied = reinterpret_cast<unsigned char*>(
|
||||
malloc(bitmap->BytesPerRow() * height));
|
||||
_cairo_malloc_ab(bitmap->BytesPerRow(), height));
|
||||
if (premultiplied)
|
||||
memcpy(premultiplied, bits, bitmap->BytesPerRow() * height);
|
||||
}
|
||||
|
|
|
|||
|
|
@ -634,9 +634,13 @@ _cairo_clip_copy_rectangle_list (cairo_clip_t *clip, cairo_gstate_t *gstate)
|
|||
return (cairo_rectangle_list_t*) &_cairo_rectangles_not_representable;
|
||||
|
||||
n_boxes = clip->has_region ? pixman_region_num_rects (&clip->region) : 1;
|
||||
rectangles = malloc (sizeof (cairo_rectangle_t)*n_boxes);
|
||||
if (rectangles == NULL)
|
||||
return (cairo_rectangle_list_t*) &_cairo_rectangles_nil;
|
||||
if (n_boxes > 0) {
|
||||
rectangles = _cairo_malloc_ab (n_boxes, sizeof (cairo_rectangle_t));
|
||||
if (rectangles == NULL)
|
||||
return (cairo_rectangle_list_t*) &_cairo_rectangles_nil;
|
||||
} else {
|
||||
rectangles = NULL;
|
||||
}
|
||||
|
||||
if (clip->has_region) {
|
||||
pixman_box16_t *boxes;
|
||||
|
|
|
|||
|
|
@ -1113,7 +1113,7 @@ _cairo_directfb_surface_set_clip_region (void *abstract_surface,
|
|||
if( surface->clips )
|
||||
free (surface->clips);
|
||||
|
||||
surface->clips = malloc (n_boxes * sizeof(DFBRegion));
|
||||
surface->clips = _cairo_malloc_ab (n_boxes, sizeof(DFBRegion));
|
||||
if (!surface->clips) {
|
||||
surface->n_clips = 0;
|
||||
return CAIRO_STATUS_NO_MEMORY;
|
||||
|
|
|
|||
|
|
@ -742,7 +742,7 @@ _get_bitmap_surface (FT_Bitmap *bitmap,
|
|||
data = bitmap->buffer;
|
||||
assert (stride == bitmap->pitch);
|
||||
} else {
|
||||
data = malloc (stride * height);
|
||||
data = _cairo_malloc_ab (height, stride);
|
||||
if (!data) {
|
||||
_cairo_error (CAIRO_STATUS_NO_MEMORY);
|
||||
return CAIRO_STATUS_NO_MEMORY;
|
||||
|
|
@ -792,7 +792,7 @@ _get_bitmap_surface (FT_Bitmap *bitmap,
|
|||
if (own_buffer) {
|
||||
data = bitmap->buffer;
|
||||
} else {
|
||||
data = malloc (stride * height);
|
||||
data = _cairo_malloc_ab (height, stride);
|
||||
if (!data) {
|
||||
_cairo_error (CAIRO_STATUS_NO_MEMORY);
|
||||
return CAIRO_STATUS_NO_MEMORY;
|
||||
|
|
|
|||
|
|
@ -197,7 +197,7 @@ _cairo_glitz_surface_get_image (cairo_glitz_surface_t *surface,
|
|||
pf.bytes_per_line = (((width * format.bpp) / 8) + 3) & -4;
|
||||
pf.scanline_order = GLITZ_PIXEL_SCANLINE_ORDER_TOP_DOWN;
|
||||
|
||||
pixels = malloc (height * pf.bytes_per_line);
|
||||
pixels = _cairo_malloc_ab (height, pf.bytes_per_line);
|
||||
if (!pixels)
|
||||
return CAIRO_STATUS_NO_MEMORY;
|
||||
|
||||
|
|
@ -627,8 +627,22 @@ _cairo_glitz_pattern_acquire_surface (cairo_pattern_t *pattern,
|
|||
|
||||
n_params = gradient->n_stops * 3 + n_base_params;
|
||||
|
||||
data = malloc (sizeof (glitz_fixed16_16_t) * n_params +
|
||||
sizeof (unsigned int) * gradient->n_stops);
|
||||
/* check for int overflow */
|
||||
{
|
||||
int size1, size2;
|
||||
if (n_params >= INT32_MAX / sizeof (glitz_fixed16_16_t) ||
|
||||
gradient->n_stops >= INT32_MAX / sizeof (unsigned int))
|
||||
return CAIRO_STATUS_NO_MEMORY;
|
||||
|
||||
size1 = n_params * sizeof (glitz_fixed16_16_t);
|
||||
size2 = gradient->n_stops * sizeof (unsigned int);
|
||||
|
||||
if (size1 >= INT32_MAX - size2)
|
||||
return CAIRO_STATUS_NO_MEMORY;
|
||||
|
||||
data = malloc (size1 + size2);
|
||||
}
|
||||
|
||||
if (!data)
|
||||
return CAIRO_STATUS_NO_MEMORY;
|
||||
|
||||
|
|
@ -1992,9 +2006,19 @@ _cairo_glitz_surface_old_show_glyphs (cairo_scaled_font_t *scaled_font,
|
|||
if (num_glyphs > N_STACK_BUF)
|
||||
{
|
||||
char *data;
|
||||
int size1, size2;
|
||||
|
||||
data = malloc (num_glyphs * sizeof (void *) +
|
||||
num_glyphs * sizeof (glitz_float_t) * 16);
|
||||
if (num_glyphs >= INT32_MAX / sizeof(void*) ||
|
||||
num_glyphs >= INT32_MAX / sizeof(glitz_float_t) ||
|
||||
(num_glyphs * sizeof(glitz_float_t)) >= INT32_MAX / 16)
|
||||
goto FAIL1;
|
||||
|
||||
size1 = num_glyphs * sizeof(void *);
|
||||
size2 = num_glyphs * sizeof(glitz_float_t) * 16;
|
||||
if (size1 >= INT32_MAX - size2)
|
||||
goto FAIL1;
|
||||
|
||||
data = malloc (size1 + size2);
|
||||
if (!data)
|
||||
goto FAIL1;
|
||||
|
||||
|
|
|
|||
|
|
@ -530,7 +530,7 @@ _cairo_gstate_set_dash (cairo_gstate_t *gstate, const double *dash, int num_dash
|
|||
return CAIRO_STATUS_SUCCESS;
|
||||
}
|
||||
|
||||
gstate->stroke_style.dash = malloc (gstate->stroke_style.num_dashes * sizeof (double));
|
||||
gstate->stroke_style.dash = _cairo_malloc_ab (gstate->stroke_style.num_dashes, sizeof (double));
|
||||
if (gstate->stroke_style.dash == NULL) {
|
||||
gstate->stroke_style.num_dashes = 0;
|
||||
return CAIRO_STATUS_NO_MEMORY;
|
||||
|
|
@ -1570,7 +1570,7 @@ _cairo_gstate_show_glyphs (cairo_gstate_t *gstate,
|
|||
if (num_glyphs <= STACK_GLYPHS_LEN) {
|
||||
transformed_glyphs = stack_transformed_glyphs;
|
||||
} else {
|
||||
transformed_glyphs = malloc (num_glyphs * sizeof(cairo_glyph_t));
|
||||
transformed_glyphs = _cairo_malloc_ab (num_glyphs, sizeof(cairo_glyph_t));
|
||||
if (transformed_glyphs == NULL)
|
||||
return CAIRO_STATUS_NO_MEMORY;
|
||||
}
|
||||
|
|
@ -1615,7 +1615,7 @@ _cairo_gstate_glyph_path (cairo_gstate_t *gstate,
|
|||
if (num_glyphs < STACK_GLYPHS_LEN)
|
||||
transformed_glyphs = stack_transformed_glyphs;
|
||||
else
|
||||
transformed_glyphs = malloc (num_glyphs * sizeof(cairo_glyph_t));
|
||||
transformed_glyphs = _cairo_malloc_ab (num_glyphs, sizeof(cairo_glyph_t));
|
||||
if (transformed_glyphs == NULL)
|
||||
return CAIRO_STATUS_NO_MEMORY;
|
||||
|
||||
|
|
|
|||
|
|
@ -62,7 +62,7 @@ _cairo_hull_create (cairo_pen_vertex_t *vertices, int num_vertices)
|
|||
*extremum = vertices[0].point;
|
||||
vertices[0].point = tmp;
|
||||
|
||||
hull = malloc (num_vertices * sizeof (cairo_hull_t));
|
||||
hull = _cairo_malloc_ab (num_vertices, sizeof (cairo_hull_t));
|
||||
if (hull == NULL)
|
||||
return NULL;
|
||||
|
||||
|
|
|
|||
104
src/cairo-malloc-private.h
Normal file
104
src/cairo-malloc-private.h
Normal file
|
|
@ -0,0 +1,104 @@
|
|||
/* -*- Mode: c; tab-width: 8; c-basic-offset: 4; indent-tabs-mode: t; -*- */
|
||||
/* Cairo - a vector graphics library with display and print output
|
||||
*
|
||||
* Copyright © 2007 Mozilla Corporation
|
||||
*
|
||||
* This library is free software; you can redistribute it and/or
|
||||
* modify it either under the terms of the GNU Lesser General Public
|
||||
* License version 2.1 as published by the Free Software Foundation
|
||||
* (the "LGPL") or, at your option, under the terms of the Mozilla
|
||||
* Public License Version 1.1 (the "MPL"). If you do not alter this
|
||||
* notice, a recipient may use your version of this file under either
|
||||
* the MPL or the LGPL.
|
||||
*
|
||||
* You should have received a copy of the LGPL along with this library
|
||||
* in the file COPYING-LGPL-2.1; if not, write to the Free Software
|
||||
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
* You should have received a copy of the MPL along with this library
|
||||
* in the file COPYING-MPL-1.1
|
||||
*
|
||||
* The contents of this file are subject to the Mozilla Public License
|
||||
* Version 1.1 (the "License"); you may not use this file except in
|
||||
* compliance with the License. You may obtain a copy of the License at
|
||||
* http://www.mozilla.org/MPL/
|
||||
*
|
||||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY
|
||||
* OF ANY KIND, either express or implied. See the LGPL or the MPL for
|
||||
* the specific language governing rights and limitations.
|
||||
*
|
||||
* The Original Code is the cairo graphics library.
|
||||
*
|
||||
* The Initial Developer of the Original Code is Mozilla Corporation
|
||||
*
|
||||
* Contributor(s):
|
||||
* Vladimir Vukicevic <vladimir@pobox.com>
|
||||
*/
|
||||
|
||||
#ifndef CAIRO_MALLOC_PRIVATE_H
|
||||
#define CAIRO_MALLOC_PRIVATE_H
|
||||
|
||||
#include "cairo-wideint-private.h"
|
||||
|
||||
/**
|
||||
* _cairo_malloc_ab:
|
||||
* @n: number of elements to allocate
|
||||
* @size: size of each element
|
||||
*
|
||||
* Allocates @a*@size memory using malloc(), taking care to not
|
||||
* overflow when doing the multiplication. Behaves much like
|
||||
* calloc(), except that the returned memory is not set to zero.
|
||||
* The memory should be freed using free().
|
||||
*
|
||||
* @size should be a constant so that the compiler can optimize
|
||||
* out a constant division.
|
||||
*
|
||||
* Return value: A pointer to the newly allocated memory, or %NULL in
|
||||
* case of malloc() failure or overflow.
|
||||
*/
|
||||
|
||||
#define _cairo_malloc_ab(a, size) \
|
||||
((unsigned) (a) >= INT32_MAX / (unsigned) (size) ? NULL : \
|
||||
malloc((unsigned) (a) * (unsigned) (size)))
|
||||
|
||||
/**
|
||||
* _cairo_malloc_abc:
|
||||
* @a: first factor of number of elements to allocate
|
||||
* @b: second factor of number of elements to allocate
|
||||
* @size: size of each element
|
||||
*
|
||||
* Allocates @a*@b*@size memory using malloc(), taking care to not
|
||||
* overflow when doing the multiplication. Behaves like
|
||||
* _cairo_malloc_ab(). The memory should be freed using free().
|
||||
*
|
||||
* @size should be a constant so that the compiler can optimize
|
||||
* out a constant division.
|
||||
*
|
||||
* Return value: A pointer to the newly allocated memory, or %NULL in
|
||||
* case of malloc() failure or overflow.
|
||||
*/
|
||||
|
||||
#define _cairo_malloc_abc(a, b, size) \
|
||||
((unsigned) (a) >= INT32_MAX / (unsigned) (b) ? NULL : \
|
||||
(unsigned) ((a)*(b)) >= INT32_MAX / (unsigned) (size) ? NULL : \
|
||||
malloc((unsigned) (a) * (unsigned) (b) * (unsigned) size))
|
||||
|
||||
/**
|
||||
* _cairo_malloc_ab_plus_c:
|
||||
* @n: number of elements to allocate
|
||||
* @size: size of each element
|
||||
* @k: additional size to allocate
|
||||
*
|
||||
* Allocates @a*@ksize+@k memory using malloc(), taking care to not
|
||||
* overflow when doing the arithmetic. Behaves like
|
||||
* _cairo_malloc_ab(). The memory should be freed using free().
|
||||
*
|
||||
* Return value: A pointer to the newly allocated memory, or %NULL in
|
||||
* case of malloc() failure or overflow.
|
||||
*/
|
||||
|
||||
#define _cairo_malloc_ab_plus_c(n, size, k) \
|
||||
((unsigned) (n) >= INT32_MAX / (unsigned) (size) ? NULL : \
|
||||
(unsigned) (k) >= INT32_MAX - (unsigned) (n) * (unsigned) (size) ? NULL : \
|
||||
malloc((unsigned) (n) * (unsigned) (size) + (unsigned) (k)))
|
||||
|
||||
#endif /* CAIRO_MALLOC_PRIVATE_H */
|
||||
|
|
@ -439,7 +439,7 @@ _cairo_meta_surface_show_glyphs (void *abstract_surface,
|
|||
if (status)
|
||||
goto CLEANUP_COMMAND;
|
||||
|
||||
command->glyphs = malloc (sizeof (cairo_glyph_t) * num_glyphs);
|
||||
command->glyphs = _cairo_malloc_ab (num_glyphs, sizeof (cairo_glyph_t));
|
||||
if (command->glyphs == NULL) {
|
||||
status = CAIRO_STATUS_NO_MEMORY;
|
||||
goto CLEANUP_SOURCE;
|
||||
|
|
@ -735,7 +735,7 @@ _cairo_meta_surface_replay (cairo_surface_t *surface,
|
|||
int i, num_glyphs = command->show_glyphs.num_glyphs;
|
||||
|
||||
if (has_device_transform) {
|
||||
dev_glyphs = malloc (sizeof (cairo_glyph_t) * num_glyphs);
|
||||
dev_glyphs = _cairo_malloc_ab (num_glyphs, sizeof (cairo_glyph_t));
|
||||
if (dev_glyphs == NULL) {
|
||||
status = CAIRO_STATUS_NO_MEMORY;
|
||||
break;
|
||||
|
|
|
|||
|
|
@ -296,8 +296,9 @@ _cairo_os2_surface_blit_pixels (cairo_os2_surface_t *surface,
|
|||
ULONG ulPixels;
|
||||
|
||||
/* allocate temporary pixel buffer */
|
||||
pchPixBuf = (unsigned char *) malloc (3 * surface->bitmap_info.cx *
|
||||
surface->bitmap_info.cy);
|
||||
pchPixBuf = (unsigned char *) _cairo_malloc_abc (surface->bitmap_info.cy,
|
||||
surface->bitmap_info.cx,
|
||||
3);
|
||||
pchPixSource = surface->pixels; /* start at beginning of pixel buffer */
|
||||
pBufStart = pchPixBuf; /* remember beginning of the new pixel buffer */
|
||||
|
||||
|
|
@ -713,7 +714,7 @@ cairo_os2_surface_create (HPS hps_client_window,
|
|||
local_os2_surface->bitmap_info.cBitCount = 32;
|
||||
|
||||
/* Allocate memory for pixels */
|
||||
local_os2_surface->pixels = (unsigned char *) malloc (width * height * 4);
|
||||
local_os2_surface->pixels = (unsigned char *) _cairo_malloc_abc (height, width, 4);
|
||||
if (!(local_os2_surface->pixels)) {
|
||||
/* Not enough memory for the pixels! */
|
||||
DosCloseEventSem (local_os2_surface->hev_pixel_array_came_back);
|
||||
|
|
@ -783,7 +784,7 @@ cairo_os2_surface_set_size (cairo_surface_t *surface,
|
|||
}
|
||||
|
||||
/* Allocate memory for new stuffs */
|
||||
pchNewPixels = (unsigned char *) malloc (new_width * new_height * 4);
|
||||
pchNewPixels = (unsigned char *) _cairo_malloc_abc (new_height, new_width, 4);
|
||||
if (!pchNewPixels) {
|
||||
/* Not enough memory for the pixels!
|
||||
* Everything remains the same!
|
||||
|
|
|
|||
|
|
@ -381,7 +381,7 @@ _cairo_path_create_internal (cairo_path_fixed_t *path_fixed,
|
|||
return (cairo_path_t*) &_cairo_path_nil;
|
||||
}
|
||||
|
||||
path->data = malloc (path->num_data * sizeof (cairo_path_data_t));
|
||||
path->data = _cairo_malloc_ab (path->num_data, sizeof (cairo_path_data_t));
|
||||
if (path->data == NULL) {
|
||||
free (path);
|
||||
return (cairo_path_t*) &_cairo_path_nil;
|
||||
|
|
|
|||
|
|
@ -133,8 +133,8 @@ _cairo_gradient_pattern_init_copy (cairo_gradient_pattern_t *pattern,
|
|||
pattern->stops = pattern->stops_embedded;
|
||||
else if (other->stops)
|
||||
{
|
||||
pattern->stops = malloc (other->stops_size *
|
||||
sizeof (pixman_gradient_stop_t));
|
||||
pattern->stops = _cairo_malloc_ab (other->stops_size,
|
||||
sizeof (pixman_gradient_stop_t));
|
||||
if (pattern->stops == NULL) {
|
||||
pattern->stops_size = 0;
|
||||
pattern->n_stops = 0;
|
||||
|
|
@ -757,7 +757,7 @@ _cairo_pattern_gradient_grow (cairo_gradient_pattern_t *pattern)
|
|||
assert (pattern->n_stops <= pattern->stops_size);
|
||||
|
||||
if (pattern->stops == pattern->stops_embedded) {
|
||||
new_stops = malloc (new_size * sizeof (pixman_gradient_stop_t));
|
||||
new_stops = _cairo_malloc_ab (new_size, sizeof (pixman_gradient_stop_t));
|
||||
if (new_stops)
|
||||
memcpy (new_stops, pattern->stops, old_size * sizeof (pixman_gradient_stop_t));
|
||||
} else {
|
||||
|
|
|
|||
|
|
@ -1262,7 +1262,7 @@ _cairo_pdf_surface_emit_pattern_stops (cairo_pdf_surface_t *surface,
|
|||
color_function->id = 0;
|
||||
alpha_function->id = 0;
|
||||
|
||||
allstops = malloc ((pattern->n_stops + 2) * sizeof (cairo_pdf_color_stop_t));
|
||||
allstops = _cairo_malloc_ab ((pattern->n_stops + 2), sizeof (cairo_pdf_color_stop_t));
|
||||
if (allstops == NULL)
|
||||
return CAIRO_STATUS_NO_MEMORY;
|
||||
|
||||
|
|
@ -2726,13 +2726,13 @@ _cairo_pdf_surface_emit_type3_font_subset (cairo_pdf_surface_t *surface,
|
|||
cairo_box_t font_bbox = {{0,0},{0,0}};
|
||||
cairo_box_t bbox = {{0,0},{0,0}};
|
||||
|
||||
glyphs = malloc (font_subset->num_glyphs * sizeof (cairo_pdf_resource_t));
|
||||
glyphs = _cairo_malloc_ab (font_subset->num_glyphs, sizeof (cairo_pdf_resource_t));
|
||||
if (glyphs == NULL) {
|
||||
_cairo_surface_set_error (&surface->base, CAIRO_STATUS_NO_MEMORY);
|
||||
return CAIRO_STATUS_NO_MEMORY;
|
||||
}
|
||||
|
||||
widths = malloc (font_subset->num_glyphs * sizeof (double));
|
||||
widths = _cairo_malloc_ab (font_subset->num_glyphs, sizeof (double));
|
||||
if (widths == NULL) {
|
||||
free (glyphs);
|
||||
_cairo_surface_set_error (&surface->base, CAIRO_STATUS_NO_MEMORY);
|
||||
|
|
|
|||
|
|
@ -78,7 +78,7 @@ _cairo_pen_init (cairo_pen_t *pen,
|
|||
radius,
|
||||
ctm);
|
||||
|
||||
pen->vertices = malloc (pen->num_vertices * sizeof (cairo_pen_vertex_t));
|
||||
pen->vertices = _cairo_malloc_ab (pen->num_vertices, sizeof (cairo_pen_vertex_t));
|
||||
if (pen->vertices == NULL) {
|
||||
return CAIRO_STATUS_NO_MEMORY;
|
||||
}
|
||||
|
|
@ -119,7 +119,7 @@ _cairo_pen_init_copy (cairo_pen_t *pen, cairo_pen_t *other)
|
|||
*pen = *other;
|
||||
|
||||
if (pen->num_vertices) {
|
||||
pen->vertices = malloc (pen->num_vertices * sizeof (cairo_pen_vertex_t));
|
||||
pen->vertices = _cairo_malloc_ab (pen->num_vertices, sizeof (cairo_pen_vertex_t));
|
||||
if (pen->vertices == NULL) {
|
||||
return CAIRO_STATUS_NO_MEMORY;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -128,7 +128,7 @@ write_png (cairo_surface_t *surface,
|
|||
else if (status != CAIRO_STATUS_SUCCESS)
|
||||
return CAIRO_STATUS_SURFACE_TYPE_MISMATCH;
|
||||
|
||||
rows = malloc (image->height * sizeof(png_byte*));
|
||||
rows = _cairo_malloc_ab (image->height, sizeof(png_byte*));
|
||||
if (rows == NULL) {
|
||||
status = CAIRO_STATUS_NO_MEMORY;
|
||||
goto BAIL1;
|
||||
|
|
@ -429,11 +429,11 @@ read_png (png_rw_ptr read_func,
|
|||
png_read_update_info (png, info);
|
||||
|
||||
pixel_size = 4;
|
||||
data = malloc (png_width * png_height * pixel_size);
|
||||
data = _cairo_malloc_abc (png_height, png_width, pixel_size);
|
||||
if (data == NULL)
|
||||
goto BAIL;
|
||||
|
||||
row_pointers = malloc (png_height * sizeof(char *));
|
||||
row_pointers = _cairo_malloc_ab (png_height, sizeof(char *));
|
||||
if (row_pointers == NULL)
|
||||
goto BAIL;
|
||||
|
||||
|
|
|
|||
|
|
@ -93,7 +93,7 @@ _cairo_polygon_grow (cairo_polygon_t *polygon)
|
|||
assert (polygon->num_edges <= polygon->edges_size);
|
||||
|
||||
if (polygon->edges == polygon->edges_embedded) {
|
||||
new_edges = malloc (new_size * sizeof (cairo_edge_t));
|
||||
new_edges = _cairo_malloc_ab (new_size, sizeof (cairo_edge_t));
|
||||
if (new_edges)
|
||||
memcpy (new_edges, polygon->edges, old_size * sizeof (cairo_edge_t));
|
||||
} else {
|
||||
|
|
|
|||
|
|
@ -2037,7 +2037,7 @@ _cairo_ps_surface_stroke (void *abstract_surface,
|
|||
* can modify some of the values.
|
||||
*/
|
||||
if (num_dashes % 2) {
|
||||
dash = malloc (2 * num_dashes * sizeof (double));
|
||||
dash = _cairo_malloc_abc (num_dashes, 2, sizeof (double));
|
||||
if (dash == NULL)
|
||||
return CAIRO_STATUS_NO_MEMORY;
|
||||
|
||||
|
|
@ -2215,7 +2215,7 @@ _cairo_ps_surface_show_glyphs (void *abstract_surface,
|
|||
num_glyphs_unsigned = num_glyphs;
|
||||
|
||||
_cairo_ps_surface_emit_pattern (surface, source);
|
||||
glyph_ids = malloc (num_glyphs_unsigned*sizeof (cairo_ps_glyph_id_t));
|
||||
glyph_ids = _cairo_malloc_ab (num_glyphs_unsigned, sizeof (cairo_ps_glyph_id_t));
|
||||
if (glyph_ids == NULL)
|
||||
return CAIRO_STATUS_NO_MEMORY;
|
||||
|
||||
|
|
|
|||
|
|
@ -1255,7 +1255,7 @@ _cairo_quartz_surface_stroke (void *abstract_surface,
|
|||
float *fdash = sdash;
|
||||
unsigned int k;
|
||||
if (style->num_dashes > STATIC_DASH)
|
||||
fdash = malloc (sizeof(float)*style->num_dashes);
|
||||
fdash = _cairo_malloc_ab (style->num_dashes, sizeof (float));
|
||||
|
||||
for (k = 0; k < style->num_dashes; k++)
|
||||
fdash[k] = (float) style->dash[k];
|
||||
|
|
@ -1394,8 +1394,8 @@ _cairo_quartz_surface_show_glyphs (void *abstract_surface,
|
|||
CGContextSetFontSize (surface->cgContext, 1.0);
|
||||
|
||||
if (num_glyphs > STATIC_BUF_SIZE) {
|
||||
cg_glyphs = (CGGlyph*) malloc(sizeof(CGGlyph) * num_glyphs);
|
||||
cg_advances = (CGSize*) malloc(sizeof(CGSize) * num_glyphs);
|
||||
cg_glyphs = (CGGlyph*) _cairo_malloc_ab (num_glyphs, sizeof(CGGlyph));
|
||||
cg_advances = (CGSize*) _cairo_malloc_ab (num_glyphs, sizeof(CGSize));
|
||||
}
|
||||
|
||||
xprev = glyphs[0].x;
|
||||
|
|
@ -1711,7 +1711,7 @@ cairo_quartz_surface_create (cairo_format_t format,
|
|||
return (cairo_surface_t*) &_cairo_surface_nil;
|
||||
}
|
||||
|
||||
imageData = malloc (height * stride);
|
||||
imageData = _cairo_malloc_ab (height, stride);
|
||||
if (!imageData) {
|
||||
CGColorSpaceRelease (cgColorspace);
|
||||
_cairo_error (CAIRO_STATUS_NO_MEMORY);
|
||||
|
|
|
|||
|
|
@ -390,7 +390,7 @@ _cairo_sub_font_collect (void *entry, void *closure)
|
|||
subset.num_glyphs = collection->num_glyphs;
|
||||
/* No need to check for out of memory here. If to_unicode is NULL, the PDF
|
||||
* surface does not emit an ToUnicode stream */
|
||||
subset.to_unicode = malloc (collection->num_glyphs*sizeof(unsigned long));
|
||||
subset.to_unicode = _cairo_malloc_ab (collection->num_glyphs, sizeof (unsigned long));
|
||||
if (subset.to_unicode) {
|
||||
for (j = 0; j < collection->num_glyphs; j++) {
|
||||
/* default unicode character required when mapping fails */
|
||||
|
|
@ -622,7 +622,7 @@ _cairo_scaled_font_subsets_foreach_internal (cairo_scaled_font_subsets_t
|
|||
if (! collection.glyphs_size)
|
||||
return CAIRO_STATUS_SUCCESS;
|
||||
|
||||
collection.glyphs = malloc (collection.glyphs_size * sizeof(unsigned long));
|
||||
collection.glyphs = _cairo_malloc_ab (collection.glyphs_size, sizeof(unsigned long));
|
||||
if (collection.glyphs == NULL)
|
||||
return CAIRO_STATUS_NO_MEMORY;
|
||||
|
||||
|
|
|
|||
|
|
@ -927,7 +927,7 @@ _cairo_scaled_font_text_to_glyphs (cairo_scaled_font_t *scaled_font,
|
|||
if (status)
|
||||
goto DONE;
|
||||
|
||||
*glyphs = (cairo_glyph_t *) malloc ((*num_glyphs) * (sizeof (cairo_glyph_t)));
|
||||
*glyphs = (cairo_glyph_t *) _cairo_malloc_ab ((*num_glyphs), sizeof (cairo_glyph_t));
|
||||
|
||||
if (*glyphs == NULL) {
|
||||
status = CAIRO_STATUS_NO_MEMORY;
|
||||
|
|
|
|||
|
|
@ -109,7 +109,7 @@ _cairo_spline_grow (cairo_spline_t *spline)
|
|||
assert (spline->num_points <= spline->points_size);
|
||||
|
||||
if (spline->points == spline->points_embedded) {
|
||||
new_points = malloc (new_size * sizeof (cairo_point_t));
|
||||
new_points = _cairo_malloc_ab (new_size, sizeof (cairo_point_t));
|
||||
if (new_points)
|
||||
memcpy (new_points, spline->points, old_size * sizeof (cairo_point_t));
|
||||
} else {
|
||||
|
|
|
|||
|
|
@ -62,7 +62,7 @@ _cairo_stroke_style_init_copy (cairo_stroke_style_t *style,
|
|||
if (other->dash == NULL) {
|
||||
style->dash = NULL;
|
||||
} else {
|
||||
style->dash = malloc (style->num_dashes * sizeof (double));
|
||||
style->dash = _cairo_malloc_ab (style->num_dashes, sizeof (double));
|
||||
if (style->dash == NULL)
|
||||
return CAIRO_STATUS_NO_MEMORY;
|
||||
|
||||
|
|
|
|||
|
|
@ -1166,7 +1166,7 @@ _cairo_surface_fallback_fill_rectangles (cairo_surface_t *surface,
|
|||
/* If the fetched image isn't at 0,0, we need to offset the rectangles */
|
||||
|
||||
if (state.image_rect.x != 0 || state.image_rect.y != 0) {
|
||||
offset_rects = malloc (sizeof (cairo_rectangle_int16_t) * num_rects);
|
||||
offset_rects = _cairo_malloc_ab (num_rects, sizeof (cairo_rectangle_int16_t));
|
||||
if (offset_rects == NULL) {
|
||||
status = CAIRO_STATUS_NO_MEMORY;
|
||||
goto DONE;
|
||||
|
|
@ -1222,7 +1222,7 @@ _cairo_surface_fallback_composite_trapezoids (cairo_operator_t op,
|
|||
/* If the destination image isn't at 0,0, we need to offset the trapezoids */
|
||||
|
||||
if (state.image_rect.x != 0 || state.image_rect.y != 0) {
|
||||
offset_traps = malloc (sizeof (cairo_trapezoid_t) * num_traps);
|
||||
offset_traps = _cairo_malloc_ab (num_traps, sizeof (cairo_trapezoid_t));
|
||||
if (!offset_traps) {
|
||||
status = CAIRO_STATUS_NO_MEMORY;
|
||||
goto DONE;
|
||||
|
|
|
|||
|
|
@ -1245,7 +1245,7 @@ _cairo_surface_fill_region (cairo_surface_t *surface,
|
|||
|
||||
rects = stack_rects;
|
||||
if (num_rects > ARRAY_LENGTH (stack_rects)) {
|
||||
rects = malloc (sizeof (cairo_rectangle_int16_t) * num_rects);
|
||||
rects = _cairo_malloc_ab (num_rects, sizeof (cairo_rectangle_int16_t));
|
||||
if (!rects)
|
||||
return CAIRO_STATUS_NO_MEMORY;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1220,7 +1220,7 @@ _cairo_svg_surface_emit_pattern_stops (cairo_output_stream_t *output,
|
|||
|
||||
if (emulate_reflect || reverse_stops) {
|
||||
n_stops = emulate_reflect ? pattern->n_stops * 2 - 2: pattern->n_stops;
|
||||
stops = malloc (sizeof (pixman_gradient_stop_t) * n_stops);
|
||||
stops = _cairo_malloc_ab (n_stops, sizeof (pixman_gradient_stop_t));
|
||||
|
||||
for (i = 0; i < pattern->n_stops; i++) {
|
||||
if (reverse_stops) {
|
||||
|
|
|
|||
|
|
@ -260,7 +260,7 @@ _cairo_traps_grow (cairo_traps_t *traps)
|
|||
return traps->status;
|
||||
|
||||
if (traps->traps == traps->traps_embedded) {
|
||||
new_traps = malloc (new_size * sizeof (cairo_trapezoid_t));
|
||||
new_traps = _cairo_malloc_ab (new_size, sizeof (cairo_trapezoid_t));
|
||||
if (new_traps)
|
||||
memcpy (new_traps, traps->traps, sizeof (traps->traps_embedded));
|
||||
} else {
|
||||
|
|
|
|||
|
|
@ -240,7 +240,7 @@ _cairo_utf8_to_ucs4 (const unsigned char *str,
|
|||
in = UTF8_NEXT_CHAR (in);
|
||||
}
|
||||
|
||||
str32 = malloc (sizeof (uint32_t) * (n_chars + 1));
|
||||
str32 = _cairo_malloc_ab (n_chars + 1, sizeof (uint32_t));
|
||||
if (!str32)
|
||||
return CAIRO_STATUS_NO_MEMORY;
|
||||
|
||||
|
|
@ -307,7 +307,7 @@ _cairo_utf8_to_utf16 (const unsigned char *str,
|
|||
in = UTF8_NEXT_CHAR (in);
|
||||
}
|
||||
|
||||
str16 = malloc (sizeof (uint16_t) * (n16 + 1));
|
||||
str16 = _cairo_malloc_ab (n16 + 1, sizeof (uint16_t));
|
||||
if (!str16)
|
||||
return CAIRO_STATUS_NO_MEMORY;
|
||||
|
||||
|
|
|
|||
|
|
@ -613,8 +613,8 @@ _cairo_win32_scaled_font_text_to_glyphs (void *abstract_font,
|
|||
dx = NULL;
|
||||
}
|
||||
|
||||
glyph_indices = malloc (sizeof (WCHAR) * buffer_size);
|
||||
dx = malloc (sizeof (int) * buffer_size);
|
||||
glyph_indices = _cairo_malloc_ab (buffer_size, sizeof (WCHAR));
|
||||
dx = _cairo_malloc_ab (buffer_size, sizeof (int));
|
||||
if (!glyph_indices || !dx) {
|
||||
status = CAIRO_STATUS_NO_MEMORY;
|
||||
goto FAIL2;
|
||||
|
|
@ -645,7 +645,7 @@ _cairo_win32_scaled_font_text_to_glyphs (void *abstract_font,
|
|||
}
|
||||
|
||||
*num_glyphs = gcp_results.nGlyphs;
|
||||
*glyphs = malloc (sizeof (cairo_glyph_t) * gcp_results.nGlyphs);
|
||||
*glyphs = _cairo_malloc_ab (gcp_results.nGlyphs, sizeof (cairo_glyph_t));
|
||||
if (!*glyphs) {
|
||||
status = CAIRO_STATUS_NO_MEMORY;
|
||||
goto FAIL2;
|
||||
|
|
|
|||
|
|
@ -186,7 +186,7 @@ _create_dc_and_bitmap (cairo_win32_surface_t *surface,
|
|||
}
|
||||
|
||||
if (num_palette > 2) {
|
||||
bitmap_info = malloc (sizeof (BITMAPINFOHEADER) + num_palette * sizeof (RGBQUAD));
|
||||
bitmap_info = _cairo_malloc_ab_plus_c (num_palette, sizeof(RGBQUAD), sizeof(BITMAPINFOHEADER));
|
||||
if (!bitmap_info)
|
||||
return CAIRO_STATUS_NO_MEMORY;
|
||||
} else {
|
||||
|
|
@ -1546,8 +1546,8 @@ _cairo_win32_surface_show_glyphs (void *surface,
|
|||
SetBkMode(dst->dc, TRANSPARENT);
|
||||
|
||||
if (num_glyphs > STACK_GLYPH_SIZE) {
|
||||
glyph_buf = (WORD *)malloc(num_glyphs * sizeof(WORD));
|
||||
dxy_buf = (int *)malloc(num_glyphs * 2 * sizeof(int));
|
||||
glyph_buf = (WORD *) _cairo_malloc_ab (num_glyphs, sizeof(WORD));
|
||||
dxy_buf = (int *) _cairo_malloc_abc (num_glyphs, sizeof(int), 2);
|
||||
}
|
||||
|
||||
/* It is vital that dx values for dxy_buf are calculated from the delta of
|
||||
|
|
|
|||
|
|
@ -403,7 +403,7 @@ _get_image_surface (cairo_xcb_surface_t *surface,
|
|||
bpp = _bits_per_pixel(surface->dpy, imagerep->depth);
|
||||
bytes_per_line = _bytes_per_line(surface->dpy, surface->width, bpp);
|
||||
|
||||
data = malloc (bytes_per_line * surface->height);
|
||||
data = _cairo_malloc_ab (surface->height, bytes_per_line);
|
||||
if (data == NULL) {
|
||||
free (imagerep);
|
||||
return CAIRO_STATUS_NO_MEMORY;
|
||||
|
|
@ -1328,7 +1328,7 @@ _create_trapezoid_mask (cairo_xcb_surface_t *dst,
|
|||
mask_picture = _create_a8_picture (dst, &transparent, width, height, FALSE);
|
||||
solid_picture = _create_a8_picture (dst, &solid, width, height, TRUE);
|
||||
|
||||
offset_traps = malloc (sizeof (xcb_render_trapezoid_t) * num_traps);
|
||||
offset_traps = _cairo_malloc_ab (num_traps, sizeof (xcb_render_trapezoid_t));
|
||||
if (!offset_traps)
|
||||
return XCB_NONE;
|
||||
|
||||
|
|
@ -1515,7 +1515,7 @@ _cairo_xcb_surface_set_clip_region (void *abstract_surface,
|
|||
|
||||
n_boxes = pixman_region_num_rects (region);
|
||||
if (n_boxes > 0) {
|
||||
rects = malloc (sizeof(xcb_rectangle_t) * n_boxes);
|
||||
rects = _cairo_malloc_ab (n_boxes, sizeof(xcb_rectangle_t));
|
||||
if (rects == NULL)
|
||||
return CAIRO_STATUS_NO_MEMORY;
|
||||
} else {
|
||||
|
|
@ -2360,7 +2360,7 @@ _cairo_xcb_surface_show_glyphs (void *abstract_dst,
|
|||
/* We make a copy of the glyphs so that we can elide any size-zero
|
||||
* glyphs to workaround an X server bug, (present in at least Xorg
|
||||
* 7.1 without EXA). */
|
||||
output_glyphs = malloc (num_glyphs * sizeof (cairo_glyph_t));
|
||||
output_glyphs = _cairo_malloc_ab (num_glyphs, sizeof (cairo_glyph_t));
|
||||
if (output_glyphs == NULL)
|
||||
return CAIRO_STATUS_NO_MEMORY;
|
||||
|
||||
|
|
|
|||
|
|
@ -1579,7 +1579,7 @@ _create_trapezoid_mask (cairo_xlib_surface_t *dst,
|
|||
mask_picture = _create_a8_picture (dst, &transparent, width, height, FALSE);
|
||||
solid_picture = _create_a8_picture (dst, &solid, width, height, TRUE);
|
||||
|
||||
offset_traps = malloc (sizeof (XTrapezoid) * num_traps);
|
||||
offset_traps = _cairo_malloc_ab (num_traps, sizeof (XTrapezoid));
|
||||
if (!offset_traps)
|
||||
return None;
|
||||
|
||||
|
|
@ -1760,7 +1760,7 @@ _cairo_xlib_surface_set_clip_region (void *abstract_surface,
|
|||
|
||||
n_boxes = pixman_region_num_rects (region);
|
||||
if (n_boxes > ARRAY_LENGTH (surface->embedded_clip_rects)) {
|
||||
rects = malloc (sizeof(XRectangle) * n_boxes);
|
||||
rects = _cairo_malloc_ab (n_boxes, sizeof(XRectangle));
|
||||
if (rects == NULL)
|
||||
return CAIRO_STATUS_NO_MEMORY;
|
||||
}else {
|
||||
|
|
@ -2815,7 +2815,7 @@ _cairo_xlib_surface_emit_glyphs_chunk (cairo_xlib_surface_t *dst,
|
|||
if (num_elts <= STACK_ELTS_LEN) {
|
||||
elts = stack_elts;
|
||||
} else {
|
||||
elts = malloc (num_elts * sizeof (XGlyphElt8));
|
||||
elts = _cairo_malloc_ab (num_elts, sizeof (XGlyphElt8));
|
||||
if (elts == NULL)
|
||||
return CAIRO_STATUS_NO_MEMORY;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -181,6 +181,7 @@ do { \
|
|||
|
||||
#include "cairo-mutex-private.h"
|
||||
#include "cairo-wideint-private.h"
|
||||
#include "cairo-malloc-private.h"
|
||||
|
||||
typedef int32_t cairo_fixed_16_16_t;
|
||||
typedef cairo_int64_t cairo_fixed_32_32_t;
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue