static fz_error *
loadseparation(fz_colorspace **csp, pdf_xref *xref, fz_obj *array)
{
	fz_error *error;
	struct separation *cs;
	fz_obj *nameobj = fz_arrayget(array, 1);
	fz_obj *baseobj = fz_arrayget(array, 2);
	fz_obj *tintobj = fz_arrayget(array, 3);
	fz_colorspace *base;
	pdf_function *tint;
	int n;

	pdf_logrsrc("load Separation {\n");

	if (fz_isarray(nameobj))
		n = fz_arraylen(nameobj);
	else
		n = 1;

	pdf_logrsrc("n = %d\n", n);

	error = pdf_resolve(&baseobj, xref);
	if (error)
		return error;
	error = pdf_loadcolorspace(&base, xref, baseobj);
	fz_dropobj(baseobj);
	if (error)
		return error;

	error = pdf_loadfunction(&tint, xref, tintobj);
	if (error)
	{
		fz_dropcolorspace(base);
		return error;
	}

	cs = fz_malloc(sizeof(struct separation));
	if (!cs)
	{
		pdf_dropfunction(tint);
		fz_dropcolorspace(base);
		return fz_outofmem;
	}

	initcs((fz_colorspace*)cs,
		n == 1 ? "Separation" : "DeviceN", n,
		separationtoxyz, nil, dropseparation);

	cs->base = base;
	cs->tint = tint;

	pdf_logrsrc("}\n");

	*csp = (fz_colorspace*)cs;
	return nil;
}
Example #2
0
static fz_error
loadseparation(fz_colorspace **csp, pdf_xref *xref, fz_obj *array)
{
	fz_error error;
	struct separation *cs;
	fz_obj *nameobj = fz_arrayget(array, 1);
	fz_obj *baseobj = fz_arrayget(array, 2);
	fz_obj *tintobj = fz_arrayget(array, 3);
	fz_colorspace *base;
	pdf_function *tint;
	int n;

	pdf_logrsrc("load Separation {\n");

	if (fz_isarray(nameobj))
		n = fz_arraylen(nameobj);
	else
		n = 1;

	if (n > FZ_MAXCOLORS)
		return fz_throw("too many components in colorspace");

	pdf_logrsrc("n = %d\n", n);

	error = pdf_loadcolorspace(&base, xref, baseobj);
	if (error)
		return fz_rethrow(error, "cannot load base colorspace");

	error = pdf_loadfunction(&tint, xref, tintobj);
	if (error)
	{
		fz_dropcolorspace(base);
		return fz_rethrow(error, "cannot load tint function");
	}

	cs = fz_malloc(sizeof(struct separation));

	initcs((fz_colorspace*)cs,
		n == 1 ? "Separation" : "DeviceN", n,
		separationtoxyz, nil, freeseparation);

	cs->base = fz_keepcolorspace(base);
	cs->tint = pdf_keepfunction(tint);

	fz_dropcolorspace(base);
	pdf_dropfunction(tint);

	pdf_logrsrc("}\n");

	*csp = (fz_colorspace*)cs;
	return fz_okay;
}
Example #3
0
static void
freeseparation(fz_colorspace *fzcs)
{
	struct separation *cs = (struct separation *)fzcs;
	fz_dropcolorspace(cs->base);
	pdf_dropfunction(cs->tint);
}
Example #4
0
static void
freeindexed(fz_colorspace *fzcs)
{
	pdf_indexed *cs = (pdf_indexed *)fzcs;
	if (cs->base) fz_dropcolorspace(cs->base);
	if (cs->lookup) fz_free(cs->lookup);
}
Example #5
0
fz_error *
pdf_setcolorspace(pdf_csi *csi, int what, fz_colorspace *cs)
{
	pdf_gstate *gs = csi->gstate + csi->gtop;
	fz_error *error;
	pdf_material *mat;

	error = pdf_flushtext(csi);
	if (error)
		return fz_rethrow(error, "cannot finish text node (state change)");

	mat = what == PDF_MFILL ? &gs->fill : &gs->stroke;

	fz_dropcolorspace(mat->cs);

	mat->kind = PDF_MCOLOR;
	mat->cs = fz_keepcolorspace(cs);

	mat->v[0] = 0;	/* FIXME: default color */
	mat->v[1] = 0;	/* FIXME: default color */
	mat->v[2] = 0;	/* FIXME: default color */
	mat->v[3] = 1;	/* FIXME: default color */

	if (!strcmp(cs->name, "Indexed"))
	{
		mat->kind = PDF_MINDEXED;
		mat->indexed = (pdf_indexed*)cs;
		mat->cs = mat->indexed->base;
	}

	if (!strcmp(cs->name, "Lab"))
		mat->kind = PDF_MLAB;

	return fz_okay;
}
Example #6
0
void
fz_dropshade(fz_shade *shade)
{
	if (shade && --shade->refs == 0)
	{
		if (shade->cs)
			fz_dropcolorspace(shade->cs);
		fz_free(shade->mesh);
		fz_free(shade);
	}
}
Example #7
0
void
fz_droprenderer(fz_renderer *gc)
{
	if (gc->dest) fz_droppixmap(gc->dest);
	if (gc->over) fz_droppixmap(gc->over);

	if (gc->model) fz_dropcolorspace(gc->model);
	if (gc->cache) fz_dropglyphcache(gc->cache);
	if (gc->gel) fz_dropgel(gc->gel);
	if (gc->ael) fz_dropael(gc->ael);
	fz_free(gc);
}
Example #8
0
void
fz_dropimage(fz_image *image)
{
	if (--image->refs == 0)
	{
		if (image->drop)
			image->drop(image);
		if (image->cs)
			fz_dropcolorspace(image->cs);
		fz_free(image);
	}
}
Example #9
0
static void dropitem(pdf_itemkind kind, void *val)
{
	switch (kind)
	{
	case PDF_KCOLORSPACE: fz_dropcolorspace(val); break;
	case PDF_KFUNCTION: pdf_dropfunction(val); break;
	case PDF_KXOBJECT: pdf_dropxobject(val); break;
	case PDF_KIMAGE: fz_dropimage(val); break;
	case PDF_KPATTERN: pdf_droppattern(val); break;
	case PDF_KSHADE: fz_dropshade(val); break;
	case PDF_KCMAP: pdf_dropcmap(val); break;
	case PDF_KFONT: pdf_dropfont(val); break;
	}
}
Example #10
0
fz_error *
fz_newrenderer(fz_renderer **gcp, fz_colorspace *pcm, int maskonly, int gcmem)
{
	fz_error *error;
	fz_renderer *gc;

	gc = fz_malloc(sizeof(fz_renderer));
	if (!gc)
		return fz_outofmem;

	gc->maskonly = maskonly;
	gc->model = pcm;
	gc->cache = nil;
	gc->gel = nil;
	gc->ael = nil;

	error = fz_newglyphcache(&gc->cache, gcmem / 24, gcmem);
	if (error)
		goto cleanup;

	error = fz_newgel(&gc->gel);
	if (error)
		goto cleanup;

	error = fz_newael(&gc->ael);
	if (error)
		goto cleanup;

	gc->dest = nil;
	gc->over = nil;
	gc->argb[0] = 255;
	gc->argb[1] = 0;
	gc->argb[2] = 0;
	gc->argb[3] = 0;
	gc->argb[4] = 0;
	gc->argb[5] = 0;
	gc->argb[6] = 0;
	gc->flag = 0;

	*gcp = gc;
	return fz_okay;

cleanup:
	if (gc->model) fz_dropcolorspace(gc->model);
	if (gc->cache) fz_dropglyphcache(gc->cache);
	if (gc->gel) fz_dropgel(gc->gel);
	if (gc->ael) fz_dropael(gc->ael);
	fz_free(gc);
	return error;
}
Example #11
0
void
fz_dropimage(fz_image *image)
{
#ifndef PSP
	printf("fz_dropimage, image %p, image->refs: %d\n", image, image->refs);
#endif
	if (--image->refs <= 0)
	{
		if (image->drop)
			image->drop(image);
		if (image->cs)
			fz_dropcolorspace(image->cs);
		fz_free(image);
	}
}
Example #12
0
void
pdf_setcolorspace(pdf_csi *csi, int what, fz_colorspace *colorspace)
{
	pdf_gstate *gs = csi->gstate + csi->gtop;
	pdf_material *mat;

	pdf_flushtext(csi);

	mat = what == PDF_MFILL ? &gs->fill : &gs->stroke;

	fz_dropcolorspace(mat->colorspace);

	mat->kind = PDF_MCOLOR;
	mat->colorspace = fz_keepcolorspace(colorspace);

	mat->v[0] = 0;
	mat->v[1] = 0;
	mat->v[2] = 0;
	mat->v[3] = 1;
}
Example #13
0
static fz_error
loadindexed(fz_colorspace **csp, pdf_xref *xref, fz_obj *array)
{
	fz_error error;
	pdf_indexed *cs;
	fz_obj *baseobj = fz_arrayget(array, 1);
	fz_obj *highobj = fz_arrayget(array, 2);
	fz_obj *lookup = fz_arrayget(array, 3);
	fz_colorspace *base;
	int n;

	pdf_logrsrc("load Indexed {\n");

	error = pdf_loadcolorspace(&base, xref, baseobj);
	if (error)
		return fz_rethrow(error, "cannot load base colorspace");

	pdf_logrsrc("base %s\n", base->name);

	cs = fz_malloc(sizeof(pdf_indexed));

	initcs((fz_colorspace*)cs, "Indexed", 1, nil, nil, freeindexed);

	cs->base = fz_keepcolorspace(base);
	cs->high = fz_toint(highobj);

	fz_dropcolorspace(base);

	n = base->n * (cs->high + 1);
	cs->lookup = fz_malloc(n);

	if (fz_isstring(lookup) && fz_tostrlen(lookup) == n)
	{
		unsigned char *buf;
		int i;

		pdf_logrsrc("string lookup\n");

		buf = (unsigned char *) fz_tostrbuf(lookup);
		for (i = 0; i < n; i++)
			cs->lookup[i] = buf[i];
	}
	else if (fz_isindirect(lookup))
	{
		fz_buffer *buf;
		int i;

		pdf_logrsrc("stream lookup\n");

		error = pdf_loadstream(&buf, xref, fz_tonum(lookup), fz_togen(lookup));
		if (error)
		{
			fz_dropcolorspace((fz_colorspace*)cs);
			return fz_rethrow(error, "cannot load colorpsace lookup table");
		}

		for (i = 0; i < n && i < (buf->wp - buf->rp); i++)
			cs->lookup[i] = buf->rp[i];

		fz_dropbuffer(buf);
	}
	else
		return fz_throw("cannot parse colorspace lookup table");

	pdf_logrsrc("}\n");

	*csp = (fz_colorspace*)cs;
	return fz_okay;
}
Example #14
0
static fz_error
pdf_loadimageimp(fz_pixmap **imgp, pdf_xref *xref, fz_obj *rdb, fz_obj *dict, fz_stream *cstm, int forcemask)
{
	fz_stream *stm;
	fz_pixmap *tile;
	fz_obj *obj, *res;
	fz_error error;

	int w, h, bpc, n;
	int imagemask;
	int interpolate;
	int indexed;
	fz_colorspace *colorspace;
	fz_pixmap *mask; /* explicit mask/softmask image */
	int usecolorkey;
	int colorkey[FZ_MAXCOLORS * 2];
	float decode[FZ_MAXCOLORS * 2];

	int scale;
	int stride;
	unsigned char *samples;
	int i, len;

	/* special case for JPEG2000 images */
	if (pdf_isjpximage(dict))
	{
		tile = nil;
		error = pdf_loadjpximage(&tile, xref, dict);
		if (error)
			return fz_rethrow(error, "cannot load jpx image");
		if (forcemask)
		{
			if (tile->n != 2)
			{
				fz_droppixmap(tile);
				return fz_throw("softmask must be grayscale");
			}
			mask = fz_alphafromgray(tile, 1);
			fz_droppixmap(tile);
			*imgp = mask;
			return fz_okay;
		}
		*imgp = tile;
		return fz_okay;
	}

	w = fz_toint(fz_dictgetsa(dict, "Width", "W"));
	h = fz_toint(fz_dictgetsa(dict, "Height", "H"));
	bpc = fz_toint(fz_dictgetsa(dict, "BitsPerComponent", "BPC"));
	imagemask = fz_tobool(fz_dictgetsa(dict, "ImageMask", "IM"));
	interpolate = fz_tobool(fz_dictgetsa(dict, "Interpolate", "I"));

	indexed = 0;
	usecolorkey = 0;
	colorspace = nil;
	mask = nil;

	if (imagemask)
		bpc = 1;

	if (w == 0)
		return fz_throw("image width is zero");
	if (h == 0)
		return fz_throw("image height is zero");
	if (bpc == 0)
		return fz_throw("image depth is zero");
	if (w > (1 << 16))
		return fz_throw("image is too wide");
	if (h > (1 << 16))
		return fz_throw("image is too high");

	obj = fz_dictgetsa(dict, "ColorSpace", "CS");
	if (obj && !imagemask && !forcemask)
	{
		/* colorspace resource lookup is only done for inline images */
		if (fz_isname(obj))
		{
			res = fz_dictget(fz_dictgets(rdb, "ColorSpace"), obj);
			if (res)
				obj = res;
		}

		error = pdf_loadcolorspace(&colorspace, xref, obj);
		if (error)
			return fz_rethrow(error, "cannot load image colorspace");

		if (!strcmp(colorspace->name, "Indexed"))
			indexed = 1;

		n = colorspace->n;
	}
	else
	{
		n = 1;
	}

	obj = fz_dictgetsa(dict, "Decode", "D");
	if (obj)
	{
		for (i = 0; i < n * 2; i++)
			decode[i] = fz_toreal(fz_arrayget(obj, i));
	}
	else
	{
		float maxval = indexed ? (1 << bpc) - 1 : 1;
		for (i = 0; i < n * 2; i++)
			decode[i] = i & 1 ? maxval : 0;
	}

	obj = fz_dictgetsa(dict, "SMask", "Mask");
	if (fz_isdict(obj))
	{
		/* Not allowed for inline images */
		if (!cstm)
		{
			error = pdf_loadimageimp(&mask, xref, rdb, obj, nil, 1);
			if (error)
			{
				if (colorspace)
					fz_dropcolorspace(colorspace);
				return fz_rethrow(error, "cannot load image mask/softmask");
			}
		}
	}
	else if (fz_isarray(obj))
	{
		usecolorkey = 1;
		for (i = 0; i < n * 2; i++)
			colorkey[i] = fz_toint(fz_arrayget(obj, i));
	}

	stride = (w * n * bpc + 7) / 8;
	samples = fz_calloc(h, stride);

	if (cstm)
	{
		stm = pdf_openinlinestream(cstm, xref, dict, stride * h);
	}
	else
	{
		error = pdf_openstream(&stm, xref, fz_tonum(dict), fz_togen(dict));
		if (error)
		{
			if (colorspace)
				fz_dropcolorspace(colorspace);
			if (mask)
				fz_droppixmap(mask);
			return fz_rethrow(error, "cannot open image data stream (%d 0 R)", fz_tonum(dict));
		}
	}

	len = fz_read(stm, samples, h * stride);
	if (len < 0)
	{
		fz_close(stm);
		if (colorspace)
			fz_dropcolorspace(colorspace);
		if (mask)
			fz_droppixmap(mask);
		return fz_rethrow(len, "cannot read image data");
	}

	/* Make sure we read the EOF marker (for inline images only) */
	if (cstm)
	{
		unsigned char tbuf[512];
		int tlen = fz_read(stm, tbuf, sizeof tbuf);
		if (tlen < 0)
			fz_catch(tlen, "ignoring error at end of image");
		if (tlen > 0)
			fz_warn("ignoring garbage at end of image");
	}

	fz_close(stm);

	/* Pad truncated images */
	if (len < stride * h)
	{
		fz_warn("padding truncated image (%d 0 R)", fz_tonum(dict));
		memset(samples + len, 0, stride * h - len);
	}

	/* Invert 1-bit image masks */
	if (imagemask)
	{
		/* 0=opaque and 1=transparent so we need to invert */
		unsigned char *p = samples;
		len = h * stride;
		for (i = 0; i < len; i++)
			p[i] = ~p[i];
	}

	pdf_logimage("size %dx%d n=%d bpc=%d imagemask=%d indexed=%d\n", w, h, n, bpc, imagemask, indexed);

	/* Unpack samples into pixmap */

	tile = fz_newpixmap(colorspace, 0, 0, w, h);

	scale = 1;
	if (!indexed)
	{
		switch (bpc)
		{
		case 1: scale = 255; break;
		case 2: scale = 85; break;
		case 4: scale = 17; break;
		}
	}

	fz_unpacktile(tile, samples, n, bpc, stride, scale);

	if (usecolorkey)
		pdf_maskcolorkey(tile, n, colorkey);

	if (indexed)
	{
		fz_pixmap *conv;

		fz_decodeindexedtile(tile, decode, (1 << bpc) - 1);

		conv = pdf_expandindexedpixmap(tile);
		fz_droppixmap(tile);
		tile = conv;
	}
	else
	{
		fz_decodetile(tile, decode);
	}

	if (colorspace)
		fz_dropcolorspace(colorspace);

	tile->mask = mask;
	tile->interpolate = interpolate;

	fz_free(samples);

	*imgp = tile;
	return fz_okay;
}
Example #15
0
static fz_error
pdf_loadjpximage(fz_pixmap **imgp, pdf_xref *xref, fz_obj *dict)
{
	fz_error error;
	fz_buffer *buf;
	fz_pixmap *img;
	fz_obj *obj;

	pdf_logimage("jpeg2000\n");

	error = pdf_loadstream(&buf, xref, fz_tonum(dict), fz_togen(dict));
	if (error)
		return fz_rethrow(error, "cannot load jpx image data");

	error = fz_loadjpximage(&img, buf->data, buf->len);
	if (error)
	{
		fz_dropbuffer(buf);
		return fz_rethrow(error, "cannot load jpx image");
	}

	fz_dropbuffer(buf);

	obj = fz_dictgetsa(dict, "SMask", "Mask");
	if (fz_isdict(obj))
	{
		error = pdf_loadimageimp(&img->mask, xref, nil, obj, nil, 1);
		if (error)
		{
			fz_droppixmap(img);
			return fz_rethrow(error, "cannot load image mask/softmask");
		}
	}

	obj = fz_dictgets(dict, "ColorSpace");
	if (obj)
	{
		fz_colorspace *original = img->colorspace;
		img->colorspace = nil;

		error = pdf_loadcolorspace(&img->colorspace, xref, obj);
		if (error)
		{
			fz_dropcolorspace(original);
			return fz_rethrow(error, "cannot load image colorspace");
		}

		if (original->n != img->colorspace->n)
		{
			fz_warn("jpeg-2000 colorspace (%s) does not match promised colorspace (%s)", original->name, img->colorspace->name);
			fz_dropcolorspace(img->colorspace);
			img->colorspace = original;
		}
		else
			fz_dropcolorspace(original);

		if (!strcmp(img->colorspace->name, "Indexed"))
		{
			fz_pixmap *conv;
			conv = pdf_expandindexedpixmap(img);
			fz_droppixmap(img);
			img = conv;
		}
	}

	*imgp = img;
	return fz_okay;
}
static fz_error *
loadindexed(fz_colorspace **csp, pdf_xref *xref, fz_obj *array)
{
	fz_error *error;
	pdf_indexed *cs;
	fz_obj *baseobj = fz_arrayget(array, 1);
	fz_obj *highobj = fz_arrayget(array, 2);
	fz_obj *lookup = fz_arrayget(array, 3);
	fz_colorspace *base;
	int n;

	pdf_logrsrc("load Indexed {\n");

	error = pdf_resolve(&baseobj, xref);
	if (error)
		return error;
	error = pdf_loadcolorspace(&base, xref, baseobj);
	fz_dropobj(baseobj);
	if (error)
		return error;

	pdf_logrsrc("base %s\n", base->name);

	cs = fz_malloc(sizeof(pdf_indexed));
	if (!cs)
	{
		fz_dropcolorspace(base);
		return fz_outofmem;
	}

	initcs((fz_colorspace*)cs, "Indexed", 1, nil, nil, dropindexed);

	cs->base = base;
	cs->high = fz_toint(highobj);

	n = base->n * (cs->high + 1);

	cs->lookup = fz_malloc(n);
	if (!cs->lookup)
	{
		fz_dropcolorspace((fz_colorspace*)cs);
		return fz_outofmem;
	}

	if (fz_isstring(lookup) && fz_tostrlen(lookup) == n)
	{
		unsigned char *buf;
		int i;

		pdf_logrsrc("string lookup\n");

		buf = fz_tostrbuf(lookup);
		for (i = 0; i < n; i++)
			cs->lookup[i] = buf[i];
	}

	if (fz_isindirect(lookup))
	{
		fz_buffer *buf;
		int i;

		pdf_logrsrc("stream lookup\n");

		error = pdf_loadstream(&buf, xref, fz_tonum(lookup), fz_togen(lookup));
		if (error)
		{
			fz_dropcolorspace((fz_colorspace*)cs);
			return error;
		}

		for (i = 0; i < n && i < (buf->wp - buf->rp); i++)
			cs->lookup[i] = buf->rp[i];

		fz_dropbuffer(buf);
	}

	pdf_logrsrc("}\n");

	*csp = (fz_colorspace*)cs;
	return nil;
}
Example #17
0
void
fz_dropblendnode(fz_blendnode *node)
{
	fz_dropcolorspace(node->cs);
}
Example #18
0
void
fz_dropsolidnode(fz_solidnode *node)
{
	fz_dropcolorspace(node->cs);
}