summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorTor Andersson <tor@ghostscript.com>2005-05-26 09:34:56 +0200
committerTor Andersson <tor@ghostscript.com>2005-05-26 09:34:56 +0200
commit987d58dfaf4030f43b2a8854e2d246f75465cc57 (patch)
tree430eeedbebfdc278a9fc88afa134c96dacc073b4
parent4bb1d274f49678af1612179d632ebcca7666f235 (diff)
downloadmupdf-987d58dfaf4030f43b2a8854e2d246f75465cc57.tar.xz
new stream api
-rw-r--r--Jamfile14
-rw-r--r--TODO2
-rw-r--r--apps/pdfdebug.c18
-rw-r--r--apps/samshow.c27
-rw-r--r--include/fitz.h27
-rw-r--r--include/fitz/buffer.h41
-rw-r--r--include/fitz/crypt.h9
-rw-r--r--include/fitz/file.h38
-rw-r--r--include/fitz/filter.h58
-rw-r--r--include/fitz/hash.h4
-rw-r--r--include/fitz/object.h6
-rw-r--r--include/fitz/path.h14
-rw-r--r--include/fitz/stream.h103
-rw-r--r--include/fitz/text.h22
-rw-r--r--include/fitz/tree.h7
-rw-r--r--include/mupdf/content.h2
-rw-r--r--include/mupdf/rsrc.h4
-rw-r--r--include/mupdf/syntax.h10
-rw-r--r--include/mupdf/xref.h10
-rw-r--r--include/samus.h1
-rw-r--r--include/samus/pack.h (renamed from include/samus/package.h)3
-rw-r--r--include/samus/xml.h8
-rw-r--r--include/samus/zip.h19
-rw-r--r--mupdf/pdf_cmap.c33
-rw-r--r--mupdf/pdf_function.c42
-rw-r--r--mupdf/pdf_image.c31
-rw-r--r--mupdf/pdf_interpret.c10
-rw-r--r--mupdf/pdf_lex.c14
-rw-r--r--mupdf/pdf_open.c94
-rw-r--r--mupdf/pdf_page.c30
-rw-r--r--mupdf/pdf_parse.c8
-rw-r--r--mupdf/pdf_pattern.c7
-rw-r--r--mupdf/pdf_repair.c8
-rw-r--r--mupdf/pdf_save.c66
-rw-r--r--mupdf/pdf_shade4.c51
-rw-r--r--mupdf/pdf_stream.c83
-rw-r--r--mupdf/pdf_type3.c7
-rw-r--r--mupdf/pdf_xref.c4
-rw-r--r--samus/sa_tiff.c43
-rw-r--r--samus/sa_xml.c47
-rw-r--r--samus/sa_zip.c54
-rw-r--r--stream/filt_predict.c2
-rw-r--r--stream/stm_buffer.c2
-rw-r--r--stream/stm_filec.c349
-rw-r--r--stream/stm_filer.c252
-rw-r--r--stream/stm_filew.c260
46 files changed, 621 insertions, 1323 deletions
diff --git a/Jamfile b/Jamfile
index 5e6d6cfa..7a2a613e 100644
--- a/Jamfile
+++ b/Jamfile
@@ -134,18 +134,21 @@ Library libstream :
obj_print.c
obj_simple.c
- stm_filter.c
stm_buffer.c
- stm_filec.c
- stm_filer.c
- stm_filew.c
+ stm_filter.c
+ stm_open.c
+ stm_read.c
+ stm_write.c
+ stm_misc.c
filt_pipeline.c
+ filt_arc4.c
+ filt_null.c
+
filt_a85d.c
filt_a85e.c
filt_ahxd.c
filt_ahxe.c
- filt_arc4.c
filt_dctd.c
filt_dcte.c
filt_faxd.c
@@ -155,7 +158,6 @@ Library libstream :
filt_flate.c
filt_lzwd.c
filt_lzwe.c
- filt_null.c
filt_predict.c
filt_rld.c
filt_rle.c
diff --git a/TODO b/TODO
index a55abd11..ed3adff6 100644
--- a/TODO
+++ b/TODO
@@ -1,3 +1,5 @@
+heh. bug in pdfselect on compressed object streams. gc takes forever, no objects remain...
+
lazy nametree
lazy pagetree
diff --git a/apps/pdfdebug.c b/apps/pdfdebug.c
index bb2d57e2..1ae84d7c 100644
--- a/apps/pdfdebug.c
+++ b/apps/pdfdebug.c
@@ -43,47 +43,49 @@ void printsafe(unsigned char *buf, int n)
void decodestream(pdf_xref *xref, int oid, int gid)
{
fz_error *error;
+ fz_stream *stm;
unsigned char buf[512];
safecol = 0;
- error = pdf_openstream(xref, oid, gid);
+ error = pdf_openstream(&stm, xref, oid, gid);
if (error) fz_abort(error);
while (1)
{
- int n = fz_read(xref->stream, buf, sizeof buf);
+ int n = fz_read(stm, buf, sizeof buf);
if (n == 0)
break;
if (n < 0)
- fz_abort(fz_ferror(xref->stream));
+ fz_abort(fz_throw("ioerror: read failed"));
printsafe(buf, n);
}
- pdf_closestream(xref);
+ fz_dropstream(stm);
}
void copystream(pdf_xref *xref, int oid, int gid)
{
fz_error *error;
+ fz_stream *stm;
unsigned char buf[512];
safecol = 0;
- error = pdf_openrawstream(xref, oid, gid);
+ error = pdf_openrawstream(&stm, xref, oid, gid);
if (error) fz_abort(error);
while (1)
{
- int n = fz_read(xref->stream, buf, sizeof buf);
+ int n = fz_read(stm, buf, sizeof buf);
if (n == 0)
break;
if (n < 0)
- fz_abort(fz_ferror(xref->stream));
+ fz_abort(fz_throw("ioerror: read failed"));
printsafe(buf, n);
}
- pdf_closestream(xref);
+ fz_dropstream(stm);
}
void printobject(pdf_xref *xref, int oid, int gid)
diff --git a/apps/samshow.c b/apps/samshow.c
index d84799a0..aa4030cc 100644
--- a/apps/samshow.c
+++ b/apps/samshow.c
@@ -5,8 +5,9 @@ int runzip(int argc, char **argv)
{
fz_error *error;
fz_buffer *buf;
+ fz_stream *stm;
sa_zip *zip;
- int i;
+ int i, n;
error = sa_openzip(&zip, argv[1]);
if (error)
@@ -17,13 +18,13 @@ int runzip(int argc, char **argv)
for (i = 2; i < argc; i++)
{
- error = sa_openzipentry(zip, argv[i]);
+ error = sa_openzipentry(&stm, zip, argv[i]);
if (error)
fz_abort(error);
- error = fz_readfile(&buf, zip->file);
- if (error)
- fz_abort(error);
- sa_closezipentry(zip);
+ n = fz_readall(&buf, stm);
+ if (n < 0)
+ fz_abort(fz_throw("ioerror: readall failed"));
+ fz_dropstream(stm);
fwrite(buf->rp, 1, buf->wp - buf->rp, stdout);
@@ -38,11 +39,11 @@ int runzip(int argc, char **argv)
int runxml(int argc, char **argv)
{
fz_error *error;
- fz_file *file;
+ fz_stream *file;
sa_xmlparser *parser;
sa_xmlitem *item;
- error = fz_openfile(&file, argv[1], FZ_READ);
+ error = fz_openrfile(&file, argv[1]);
if (error)
fz_abort(error);
@@ -55,19 +56,19 @@ int runxml(int argc, char **argv)
sa_debugxml(item, 0);
sa_closexml(parser);
- fz_closefile(file);
+ fz_dropstream(file);
return 0;
}
-extern fz_error *sa_readtiff(fz_file *);
+extern fz_error *sa_readtiff(fz_stream *);
int runtiff(int argc, char **argv)
{
fz_error *error;
- fz_file *file;
+ fz_stream *file;
- error = fz_openfile(&file, argv[1], FZ_READ);
+ error = fz_openrfile(&file, argv[1]);
if (error)
fz_abort(error);
@@ -75,7 +76,7 @@ int runtiff(int argc, char **argv)
if (error)
fz_abort(error);
- fz_closefile(file);
+ fz_dropstream(file);
return 0;
}
diff --git a/include/fitz.h b/include/fitz.h
index 7bcc2b01..942219bb 100644
--- a/include/fitz.h
+++ b/include/fitz.h
@@ -3,6 +3,9 @@
#endif
#define _FITZ_H_
+/*
+ * Base library
+ */
#include "fitz/sysdep.h"
#include "fitz/cpudep.h"
#include "fitz/base.h"
@@ -10,23 +13,35 @@
#include "fitz/geometry.h"
#include "fitz/hash.h"
+/*
+ * Streams and dynamic objects
+ */
+#include "fitz/crypt.h"
+#include "fitz/object.h"
+#include "fitz/buffer.h"
+#include "fitz/filter.h"
+#include "fitz/stream.h"
+
+/*
+ * Resources
+ */
#include "fitz/cmap.h"
#include "fitz/font.h"
-
#include "fitz/pixmap.h"
#include "fitz/colorspace.h"
#include "fitz/image.h"
#include "fitz/shade.h"
+/*
+ * Display tree
+ */
#include "fitz/tree.h"
#include "fitz/path.h"
#include "fitz/text.h"
+/*
+ * Renderer
+ */
#include "fitz/pathscan.h"
#include "fitz/render.h"
-#include "fitz/crypt.h"
-#include "fitz/object.h"
-#include "fitz/filter.h"
-#include "fitz/file.h"
-
diff --git a/include/fitz/buffer.h b/include/fitz/buffer.h
new file mode 100644
index 00000000..1a6f34ad
--- /dev/null
+++ b/include/fitz/buffer.h
@@ -0,0 +1,41 @@
+/*
+ * Data buffers for streams and filters.
+ *
+ * bp is the pointer to the allocated memory
+ * rp is read-position (*in->rp++ to read data)
+ * wp is write-position (*out->wp++ to write data)
+ * ep is the sentinel
+ *
+ * Only the data between rp and wp is valid data.
+ *
+ * Writers set eof to true at the end.
+ * Readers look at eof.
+ *
+ * A buffer owns the memory it has allocated, unless ownsdata is false,
+ * in which case the creator of the buffer owns it.
+ */
+
+typedef struct fz_buffer_s fz_buffer;
+
+#define FZ_BUFSIZE (8 * 1024)
+
+struct fz_buffer_s
+{
+ int refs;
+ int ownsdata;
+ unsigned char *bp;
+ unsigned char *rp;
+ unsigned char *wp;
+ unsigned char *ep;
+ int eof;
+};
+
+fz_error *fz_newbuffer(fz_buffer **bufp, int size);
+fz_error *fz_newbufferwithmemory(fz_buffer **bufp, unsigned char *data, int size);
+
+fz_error *fz_rewindbuffer(fz_buffer *buf);
+fz_error *fz_growbuffer(fz_buffer *buf);
+
+fz_buffer *fz_keepbuffer(fz_buffer *buf);
+void fz_dropbuffer(fz_buffer *buf);
+
diff --git a/include/fitz/crypt.h b/include/fitz/crypt.h
index 647a1eda..15191caa 100644
--- a/include/fitz/crypt.h
+++ b/include/fitz/crypt.h
@@ -1,3 +1,9 @@
+/*
+ * Basic crypto functions.
+ * Independent of the rest of fitz.
+ * For further encapsulation in filters, or not.
+ */
+
/* md5 digests */
typedef struct fz_md5_s fz_md5;
@@ -28,3 +34,6 @@ void fz_arc4init(fz_arc4 *state, unsigned char *key, unsigned len);
unsigned char fz_arc4next(fz_arc4 *state);
void fz_arc4encrypt(fz_arc4 *state, unsigned char *dest, unsigned char *src, unsigned len);
+/* TODO: sha1 */
+/* TODO: aes */
+
diff --git a/include/fitz/file.h b/include/fitz/file.h
deleted file mode 100644
index c87ccf5d..00000000
--- a/include/fitz/file.h
+++ /dev/null
@@ -1,38 +0,0 @@
-typedef struct fz_file_s fz_file;
-
-enum { FZ_READ, FZ_WRITE, FZ_APPEND };
-
-struct fz_file_s
-{
- int mode; /* FZ_READ or FZ_WRITE */
- int fd;
- int depth;
- fz_filter *filter;
- fz_buffer *in;
- fz_buffer *out;
- fz_error *error;
-};
-
-fz_error *fz_openfile(fz_file **filep, char *path, int mode);
-fz_error *fz_openbuffer(fz_file **filep, fz_buffer *buf, int mode);
-fz_error *fz_pushfilter(fz_file *file, fz_filter *filter);
-void fz_popfilter(fz_file *file);
-void fz_closefile(fz_file *file);
-fz_error *fz_ferror(fz_file *f);
-
-int fz_seek(fz_file *f, int ofs, int whence);
-int fz_tell(fz_file *f);
-
-int fz_readbyte(fz_file *f);
-int fz_peekbyte(fz_file *f);
-int fz_readline(fz_file *f, char *buf, int n);
-int fz_read(fz_file *f, unsigned char *buf, int n);
-
-fz_error *fz_readfile(fz_buffer **bufp, fz_file *file);
-
-int fz_printstring(fz_file *f, char *s);
-int fz_printobj(fz_file *f, fz_obj *o, int tight);
-int fz_print(fz_file *f, char *fmt, ...);
-int fz_write(fz_file *f, unsigned char *buf, int n);
-int fz_flush(fz_file *f);
-
diff --git a/include/fitz/filter.h b/include/fitz/filter.h
index bb33b8eb..f8902f98 100644
--- a/include/fitz/filter.h
+++ b/include/fitz/filter.h
@@ -1,7 +1,29 @@
-typedef struct fz_filter_s fz_filter;
-typedef struct fz_buffer_s fz_buffer;
+/*
+ * Data filters for encryption, compression and decompression.
+ *
+ * A filter has one method, process, that takes an input and an output buffer.
+ *
+ * It returns one of three statuses:
+ * ioneedin -- input buffer exhausted, please give me more data (wp-rp)
+ * ioneedout -- output buffer exhausted, please provide more space (ep-wp)
+ * iodone -- finished, please never call me again. ever!
+ * or...
+ * any other error object -- oops, something blew up.
+ *
+ * To make using the filter easier, three variables are updated:
+ * produced -- if we actually produced any new data
+ * consumed -- like above
+ * count -- number of bytes produced in total since the beginning
+ *
+ * Most filters take fz_obj as a way to specify parameters.
+ * In most cases, this is a dictionary that contains the same keys
+ * that the corresponding PDF filter would expect.
+ *
+ * The pipeline filter is special, and needs some care when chaining
+ * and unchaining new filters.
+ */
-#define FZ_BUFSIZE (32 * 1024)
+typedef struct fz_filter_s fz_filter;
#define fz_ioneedin (&fz_kioneedin)
#define fz_ioneedout (&fz_kioneedout)
@@ -11,6 +33,10 @@ extern fz_error fz_kioneedin;
extern fz_error fz_kioneedout;
extern fz_error fz_kiodone;
+/*
+ * Evil looking macro to create an initialize a filter struct.
+ */
+
#define FZ_NEWFILTER(TYPE,VAR,NAME) \
fz_error * fz_process ## NAME (fz_filter*,fz_buffer*,fz_buffer*); \
void fz_drop ## NAME (fz_filter*); \
@@ -35,35 +61,19 @@ struct fz_filter_s
int count;
};
-struct fz_buffer_s
-{
- int refs;
- int ownsdata;
- unsigned char *bp;
- unsigned char *rp;
- unsigned char *wp;
- unsigned char *ep;
- int eof;
-};
-
fz_error *fz_process(fz_filter *f, fz_buffer *in, fz_buffer *out);
fz_filter *fz_keepfilter(fz_filter *f);
void fz_dropfilter(fz_filter *f);
-fz_error *fz_newnullfilter(fz_filter **fp, int len);
-fz_error *fz_newarc4filter(fz_filter **fp, unsigned char *key, unsigned keylen);
fz_error *fz_newpipeline(fz_filter **fp, fz_filter *head, fz_filter *tail);
-
fz_error *fz_chainpipeline(fz_filter **fp, fz_filter *head, fz_filter *tail, fz_buffer *buf);
void fz_unchainpipeline(fz_filter *pipe, fz_filter **oldfp, fz_buffer **oldbp);
-fz_error *fz_newbuffer(fz_buffer **bufp, int size);
-fz_error *fz_newbufferwithdata(fz_buffer **bufp, unsigned char *data, int size);
-fz_error *fz_rewindbuffer(fz_buffer *buf);
-fz_error *fz_growbuffer(fz_buffer *buf);
-fz_buffer *fz_keepbuffer(fz_buffer *buf);
-void fz_dropbuffer(fz_buffer *buf);
+/* stop and reverse! special case needed for postscript only */
+void fz_pushbackahxd(fz_filter *filter, fz_buffer *in, fz_buffer *out, int n);
+fz_error *fz_newnullfilter(fz_filter **fp, int len);
+fz_error *fz_newarc4filter(fz_filter **fp, unsigned char *key, unsigned keylen);
fz_error *fz_newa85d(fz_filter **filterp, fz_obj *param);
fz_error *fz_newa85e(fz_filter **filterp, fz_obj *param);
fz_error *fz_newahxd(fz_filter **filterp, fz_obj *param);
@@ -83,5 +93,3 @@ fz_error *fz_newpredicte(fz_filter **filterp, fz_obj *param);
fz_error *fz_newjbig2d(fz_filter **filterp, fz_obj *param);
fz_error *fz_newjpxd(fz_filter **filterp, fz_obj *param);
-void fz_pushbackahxd(fz_filter *filter, fz_buffer *in, fz_buffer *out, int n);
-
diff --git a/include/fitz/hash.h b/include/fitz/hash.h
index 2ada17f4..5d2ec1b5 100644
--- a/include/fitz/hash.h
+++ b/include/fitz/hash.h
@@ -1,3 +1,7 @@
+/*
+ * Generic hash-table with fixed-length keys.
+ */
+
typedef struct fz_hashtable_s fz_hashtable;
fz_error *fz_newhash(fz_hashtable **tablep, int initialsize, int keylen);
diff --git a/include/fitz/object.h b/include/fitz/object.h
index 34b62f59..fe9c12e5 100644
--- a/include/fitz/object.h
+++ b/include/fitz/object.h
@@ -1,3 +1,9 @@
+/*
+ * Dynamic objects.
+ * The same type of objects as found in PDF and PostScript.
+ * Used by the filter library and the mupdf parser.
+ */
+
typedef struct fz_obj_s fz_obj;
typedef struct fz_keyval_s fz_keyval;
diff --git a/include/fitz/path.h b/include/fitz/path.h
index 75b3060d..6a7c55b7 100644
--- a/include/fitz/path.h
+++ b/include/fitz/path.h
@@ -1,3 +1,17 @@
+/*
+ * Vector path nodes in the display tree.
+ * They can be stroked and dashed, or be filled.
+ * They have a fill rule (nonzero or evenodd).
+ *
+ * When rendering, they are flattened, stroked and dashed straight
+ * into the Global Edge List.
+ *
+ * TODO flatten, stroke and dash into another path
+ * TODO set operations on flat paths (union, intersect, difference)
+ * TODO decide whether dashing should be part of the tree and renderer,
+ * or if it is something the client has to do (with a util function).
+ */
+
typedef struct fz_stroke_s fz_stroke;
typedef struct fz_dash_s fz_dash;
typedef union fz_pathel_s fz_pathel;
diff --git a/include/fitz/stream.h b/include/fitz/stream.h
new file mode 100644
index 00000000..5140fcca
--- /dev/null
+++ b/include/fitz/stream.h
@@ -0,0 +1,103 @@
+/*
+ * Stream API for Fitz.
+ * Read and write data to and from files, memory buffers and filters.
+ */
+
+typedef struct fz_stream_s fz_stream;
+
+enum { FZ_SFILE, FZ_SBUFFER, FZ_SFILTER };
+enum { FZ_SREAD, FZ_SWRITE };
+
+struct fz_stream_s
+{
+ int refs;
+ int kind;
+ int mode;
+ int dead;
+ fz_buffer *buffer;
+ fz_filter *filter;
+ fz_stream *chain;
+ int file;
+};
+
+/*
+ * Various stream creation functions.
+ */
+
+/* open() and creat() & co */
+fz_error *fz_openrfile(fz_stream **stmp, char *filename);
+fz_error *fz_openwfile(fz_stream **stmp, char *filename);
+fz_error *fz_openafile(fz_stream **stmp, char *filename);
+
+/* write to memory buffers! */
+fz_error *fz_openrmemory(fz_stream **stmp, char *buf, int len);
+fz_error *fz_openrbuffer(fz_stream **stmp, fz_buffer *buf);
+fz_error *fz_openwbuffer(fz_stream **stmp, fz_buffer *buf);
+
+/* almost like fork() exec() pipe() */
+fz_error *fz_openrfilter(fz_stream **stmp, fz_filter *flt, fz_stream *chain);
+fz_error *fz_openwfilter(fz_stream **stmp, fz_filter *flt, fz_stream *chain);
+
+/*
+ * Functions that are common to both input and output streams.
+ */
+
+/* behave like dup() */
+fz_stream *fz_keepstream(fz_stream *stm);
+
+/* essentially your close() */
+void fz_dropstream(fz_stream *stm);
+
+int fz_tell(fz_stream *stm);
+int fz_seek(fz_stream *stm, int offset, int whence);
+
+/*
+ * Input stream functions.
+ * Return EOF (-1) on errors.
+ */
+
+int fz_rtell(fz_stream *stm);
+int fz_rseek(fz_stream *stm, int offset, int whence);
+
+int fz_makedata(fz_stream *stm);
+int fz_read(fz_stream *stm, unsigned char *buf, int len);
+
+int fz_readall(fz_buffer **bufp, fz_stream *stm);
+int fz_readline(fz_stream *stm, char *buf, int max);
+
+int fz_readbytex(fz_stream *stm);
+int fz_peekbytex(fz_stream *stm);
+
+#if 1
+#define fz_readbyte fz_readbytex
+#define fz_peekbyte fz_peekbytex
+#else
+
+#define FZ_READBYTE(XXX) { \
+ fz_buffer *buf = stm->buffer; \
+ if (buf->rp == buf->wp) \
+ if (fz_makedata(stm) < 0) \
+ return EOF; \
+ return buf->rp < buf->wp ? XXX : EOF ; \
+}
+
+static inline int fz_readbyte(fz_stream *stm) FZ_READBYTE(*buf->rp++)
+static inline int fz_peekbyte(fz_stream *stm) FZ_READBYTE(*buf->rp)
+
+#endif
+
+/*
+ * Output stream functions.
+ * Return N or 0 on success, -1 on failure.
+ */
+
+int fz_wtell(fz_stream *stm);
+int fz_wseek(fz_stream *stm, int offset, int whence);
+
+int fz_write(fz_stream *stm, unsigned char *buf, int n);
+int fz_flush(fz_stream *stm);
+
+int fz_printstr(fz_stream *stm, char *s);
+int fz_printobj(fz_stream *stm, fz_obj *obj, int tight);
+int fz_print(fz_stream *stm, char *fmt, ...);
+
diff --git a/include/fitz/text.h b/include/fitz/text.h
index 8bb6ee5a..619aae83 100644
--- a/include/fitz/text.h
+++ b/include/fitz/text.h
@@ -1,3 +1,25 @@
+/*
+ * Fitz display tree text node.
+ *
+ * The text node is an optimization to reference glyphs in a font resource
+ * and specifying an individual transform matrix for each one.
+ *
+ * The trm field contains the a, b, c and d coefficients.
+ * The e and f coefficients come from the individual elements,
+ * together they form the transform matrix for the glyph.
+ *
+ * Glyphs are referenced by glyph ID.
+ * The Unicode text equivalent is kept in a separate array
+ * with indexes into the glyph array.
+ *
+
+TODO the unicode textels
+
+struct fz_textgid_s { float e, f; int gid; };
+struct fz_textucs_s { int idx; int ucs; };
+
+ */
+
typedef struct fz_textel_s fz_textel;
struct fz_textel_s
diff --git a/include/fitz/tree.h b/include/fitz/tree.h
index ced3b491..9f76f167 100644
--- a/include/fitz/tree.h
+++ b/include/fitz/tree.h
@@ -1,3 +1,10 @@
+/*
+ * The display tree is at the center of attention in Fitz.
+ * The tree and most of its minor nodes.
+ * Paths and text nodes are found elsewhere.
+ * Resources used are also found elsewhere.
+ */
+
typedef struct fz_tree_s fz_tree;
typedef struct fz_node_s fz_node;
diff --git a/include/mupdf/content.h b/include/mupdf/content.h
index adc5757a..ad6b824d 100644
--- a/include/mupdf/content.h
+++ b/include/mupdf/content.h
@@ -105,6 +105,6 @@ fz_error *pdf_showimage(pdf_csi*, pdf_image *img);
/* interpret.c */
fz_error *pdf_newcsi(pdf_csi **csip, int maskonly);
-fz_error *pdf_runcsi(pdf_csi *, pdf_xref *xref, fz_obj *rdb, fz_file *);
+fz_error *pdf_runcsi(pdf_csi *, pdf_xref *xref, fz_obj *rdb, fz_stream *);
void pdf_dropcsi(pdf_csi *csi);
diff --git a/include/mupdf/rsrc.h b/include/mupdf/rsrc.h
index 5b78a1e8..1b245987 100644
--- a/include/mupdf/rsrc.h
+++ b/include/mupdf/rsrc.h
@@ -135,7 +135,7 @@ struct pdf_image_s
fz_buffer *samples;
};
-fz_error *pdf_loadinlineimage(pdf_image **imgp, pdf_xref *xref, fz_obj *rdb, fz_obj *dict, fz_file *file);
+fz_error *pdf_loadinlineimage(pdf_image **imgp, pdf_xref *xref, fz_obj *rdb, fz_obj *dict, fz_stream *file);
fz_error *pdf_loadimage(pdf_image **imgp, pdf_xref *xref, fz_obj *obj, fz_obj *ref);
fz_error *pdf_loadtile(fz_image *image, fz_pixmap *tile);
@@ -197,7 +197,7 @@ struct pdf_font_s
};
/* cmap.c */
-fz_error *pdf_parsecmap(fz_cmap **cmapp, fz_file *file);
+fz_error *pdf_parsecmap(fz_cmap **cmapp, fz_stream *file);
fz_error *pdf_loadembeddedcmap(fz_cmap **cmapp, pdf_xref *xref, fz_obj *ref);
fz_error *pdf_loadsystemcmap(fz_cmap **cmapp, char *name);
fz_error *pdf_makeidentitycmap(fz_cmap **cmapp, int wmode, int bytes);
diff --git a/include/mupdf/syntax.h b/include/mupdf/syntax.h
index 87fc946a..d5598cd5 100644
--- a/include/mupdf/syntax.h
+++ b/include/mupdf/syntax.h
@@ -17,13 +17,13 @@ enum
};
/* lex.c */
-int pdf_lex(fz_file *f, unsigned char *buf, int n, int *len);
+int pdf_lex(fz_stream *f, unsigned char *buf, int n, int *len);
/* parse.c */
-fz_error *pdf_parsearray(fz_obj **op, fz_file *f, char *buf, int cap);
-fz_error *pdf_parsedict(fz_obj **op, fz_file *f, char *buf, int cap);
-fz_error *pdf_parsestmobj(fz_obj **op, fz_file *f, char *buf, int cap);
-fz_error *pdf_parseindobj(fz_obj **op, fz_file *f, char *buf, int cap, int *oid, int *gid, int *stmofs);
+fz_error *pdf_parsearray(fz_obj **op, fz_stream *f, char *buf, int cap);
+fz_error *pdf_parsedict(fz_obj **op, fz_stream *f, char *buf, int cap);
+fz_error *pdf_parsestmobj(fz_obj **op, fz_stream *f, char *buf, int cap);
+fz_error *pdf_parseindobj(fz_obj **op, fz_stream *f, char *buf, int cap, int *oid, int *gid, int *stmofs);
fz_rect pdf_torect(fz_obj *array);
fz_matrix pdf_tomatrix(fz_obj *array);
diff --git a/include/mupdf/xref.h b/include/mupdf/xref.h
index d16d81f4..3143719d 100644
--- a/include/mupdf/xref.h
+++ b/include/mupdf/xref.h
@@ -7,8 +7,7 @@ typedef struct pdf_xref_s pdf_xref;
struct pdf_xref_s
{
- fz_file *file;
- fz_file *stream;
+ fz_stream *file;
float version;
int startxref;
pdf_crypt *crypt;
@@ -61,13 +60,12 @@ fz_error *pdf_loadobject(fz_obj **objp, pdf_xref *, int oid, int gen);
fz_error *pdf_loadindirect(fz_obj **objp, pdf_xref *, fz_obj *ref);
fz_error *pdf_resolve(fz_obj **reforobj, pdf_xref *);
-fz_error *pdf_decodefilter(fz_filter **filterp, fz_obj *stmobj);
int pdf_isstream(pdf_xref *xref, int oid, int gen);
+fz_error *pdf_buildinlinefilter(fz_filter **filterp, fz_obj *stmobj);
fz_error *pdf_loadrawstream(fz_buffer **bufp, pdf_xref *xref, int oid, int gen);
fz_error *pdf_loadstream(fz_buffer **bufp, pdf_xref *xref, int oid, int gen);
-fz_error *pdf_openrawstream(pdf_xref *, int oid, int gen);
-fz_error *pdf_openstream(pdf_xref *, int oid, int gen);
-void pdf_closestream(pdf_xref *);
+fz_error *pdf_openrawstream(fz_stream **stmp, pdf_xref *, int oid, int gen);
+fz_error *pdf_openstream(fz_stream **stmp, pdf_xref *, int oid, int gen);
fz_error *pdf_garbagecollect(pdf_xref *xref);
fz_error *pdf_transplant(pdf_xref *dst, pdf_xref *src, fz_obj **newp, fz_obj *old);
diff --git a/include/samus.h b/include/samus.h
index 215fe573..dd5e4656 100644
--- a/include/samus.h
+++ b/include/samus.h
@@ -9,4 +9,5 @@
#include "samus/zip.h"
#include "samus/xml.h"
+#include "samus/pack.h"
diff --git a/include/samus/package.h b/include/samus/pack.h
index 4c8512f7..bba55d2f 100644
--- a/include/samus/package.h
+++ b/include/samus/pack.h
@@ -6,7 +6,6 @@ typedef struct sa_package_s sa_package;
fz_error *sa_openpackage(sa_package **packp, char *filename);
char *sa_accesspart(sa_package *pack, char *partname);
-fz_error *sa_openpart(fz_file **filep, sa_package *pack, char *partname);
-void sa_closepart(sa_package *pack, fz_file *file);
+fz_error *sa_openpart(fz_stream **filep, sa_package *pack, char *partname);
void sa_closepackage(sa_package *pack);
diff --git a/include/samus/xml.h b/include/samus/xml.h
index 56c19b0a..b72fbe56 100644
--- a/include/samus/xml.h
+++ b/include/samus/xml.h
@@ -7,7 +7,7 @@
typedef struct sa_xmlparser_s sa_xmlparser;
typedef struct sa_xmlitem_s sa_xmlitem;
-fz_error *sa_openxml(sa_xmlparser **spp, fz_file *file, int ns);
+fz_error *sa_openxml(sa_xmlparser **spp, fz_stream *file, int ns);
void sa_debugxml(sa_xmlitem *item, int level);
void sa_closexml(sa_xmlparser *sp);
@@ -15,12 +15,6 @@ sa_xmlitem *sa_xmlnext(sa_xmlparser *sp);
void sa_xmldown(sa_xmlparser *sp);
void sa_xmlup(sa_xmlparser *sp);
-int sa_isxmlerror(sa_xmlitem *item);
-int sa_isxmltext(sa_xmlitem *item);
-int sa_isxmltag(sa_xmlitem *item);
-
-char *sa_xmlerror(sa_xmlitem *item);
char *sa_xmlname(sa_xmlitem *item);
char *sa_xmlatt(sa_xmlitem *item, char *att);
-char *sa_xmltext(sa_xmlitem *item);
diff --git a/include/samus/zip.h b/include/samus/zip.h
index 2d3635f7..e06e1e90 100644
--- a/include/samus/zip.h
+++ b/include/samus/zip.h
@@ -3,27 +3,10 @@
*/
typedef struct sa_zip_s sa_zip;
-typedef struct sa_zipent_s sa_zipent;
-
-struct sa_zipent_s
-{
- unsigned offset;
- unsigned csize;
- unsigned usize;
- char *name;
-};
-
-struct sa_zip_s
-{
- fz_file *file;
- int len;
- sa_zipent *table;
-};
fz_error *sa_openzip(sa_zip **zipp, char *filename);
void sa_debugzip(sa_zip *zip);
void sa_closezip(sa_zip *zip);
int sa_accesszipentry(sa_zip *zip, char *name);
-fz_error *sa_openzipentry(sa_zip *zip, char *name);
-void sa_closezipentry(sa_zip *zip);
+fz_error *sa_openzipentry(fz_stream **stmp, sa_zip *zip, char *name);
diff --git a/mupdf/pdf_cmap.c b/mupdf/pdf_cmap.c
index 5029ae4a..45a0eed7 100644
--- a/mupdf/pdf_cmap.c
+++ b/mupdf/pdf_cmap.c
@@ -40,7 +40,7 @@ static int codefromstring(unsigned char *buf, int len)
return a;
}
-static int mylex(fz_file *file, char *buf, int n, int *sl)
+static int mylex(fz_stream *file, char *buf, int n, int *sl)
{
int token = pdf_lex(file, buf, n, sl);
if (token == PDF_TKEYWORD)
@@ -48,7 +48,7 @@ static int mylex(fz_file *file, char *buf, int n, int *sl)
return token;
}
-static fz_error *parsecmapname(fz_cmap *cmap, fz_file *file)
+static fz_error *parsecmapname(fz_cmap *cmap, fz_stream *file)
{
char buf[256];
int token;
@@ -63,7 +63,7 @@ static fz_error *parsecmapname(fz_cmap *cmap, fz_file *file)
return fz_throw("syntaxerror in CMap after /CMapName");
}
-static fz_error *parsewmode(fz_cmap *cmap, fz_file *file)
+static fz_error *parsewmode(fz_cmap *cmap, fz_stream *file)
{
char buf[256];
int token;
@@ -78,7 +78,7 @@ static fz_error *parsewmode(fz_cmap *cmap, fz_file *file)
return fz_throw("syntaxerror in CMap after /WMode");
}
-static fz_error *parsecodespacerange(fz_cmap *cmap, fz_file *file)
+static fz_error *parsecodespacerange(fz_cmap *cmap, fz_stream *file)
{
char buf[256];
int token;
@@ -113,7 +113,7 @@ static fz_error *parsecodespacerange(fz_cmap *cmap, fz_file *file)
return fz_throw("syntaxerror in CMap codespacerange section");
}
-static fz_error *parsecidrange(fz_cmap *cmap, fz_file *file)
+static fz_error *parsecidrange(fz_cmap *cmap, fz_stream *file)
{
char buf[256];
int token;
@@ -154,7 +154,7 @@ cleanup:
return fz_throw("syntaxerror in CMap cidrange section");
}
-static fz_error *parsecidchar(fz_cmap *cmap, fz_file *file)
+static fz_error *parsecidchar(fz_cmap *cmap, fz_stream *file)
{
char buf[256];
int token;
@@ -189,7 +189,7 @@ cleanup:
return fz_throw("syntaxerror in CMap cidchar section");
}
-static fz_error *parsebfrange(fz_cmap *cmap, fz_file *file)
+static fz_error *parsebfrange(fz_cmap *cmap, fz_stream *file)
{
char buf[256];
int token;
@@ -231,7 +231,7 @@ cleanup:
return fz_throw("syntaxerror in CMap bfrange section");
}
-static fz_error *parsebfchar(fz_cmap *cmap, fz_file *file)
+static fz_error *parsebfchar(fz_cmap *cmap, fz_stream *file)
{
char buf[256];
int token;
@@ -268,7 +268,7 @@ cleanup:
}
fz_error *
-pdf_parsecmap(fz_cmap **cmapp, fz_file *file)
+pdf_parsecmap(fz_cmap **cmapp, fz_stream *file)
{
fz_error *error;
fz_cmap *cmap;
@@ -377,6 +377,7 @@ pdf_loadembeddedcmap(fz_cmap **cmapp, pdf_xref *xref, fz_obj *stmref)
{
fz_obj *stmobj = stmref;
fz_error *error = nil;
+ fz_stream *file;
fz_cmap *cmap = nil;
fz_cmap *usecmap;
fz_obj *wmode;
@@ -394,15 +395,15 @@ pdf_loadembeddedcmap(fz_cmap **cmapp, pdf_xref *xref, fz_obj *stmref)
if (error)
return error;
- error = pdf_openstream(xref, fz_tonum(stmref), fz_togen(stmref));
+ error = pdf_openstream(&file, xref, fz_tonum(stmref), fz_togen(stmref));
if (error)
goto cleanup;
- error = pdf_parsecmap(&cmap, xref->file);
+ error = pdf_parsecmap(&cmap, file);
if (error)
goto cleanup;
- pdf_closestream(xref);
+ fz_dropstream(file);
wmode = fz_dictgets(stmobj, "WMode");
if (fz_isint(wmode))
@@ -456,7 +457,7 @@ fz_error *
pdf_loadsystemcmap(fz_cmap **cmapp, char *name)
{
fz_error *error = nil;
- fz_file *file;
+ fz_stream *file;
char *cmapdir;
char *usecmapname;
fz_cmap *usecmap;
@@ -473,7 +474,7 @@ pdf_loadsystemcmap(fz_cmap **cmapp, char *name)
strlcat(path, "/", sizeof path);
strlcat(path, name, sizeof path);
- error = fz_openfile(&file, path, FZ_READ);
+ error = fz_openrfile(&file, path);
if (error)
goto cleanup;
@@ -481,7 +482,7 @@ pdf_loadsystemcmap(fz_cmap **cmapp, char *name)
if (error)
goto cleanup;
- fz_closefile(file);
+ fz_dropstream(file);
usecmapname = fz_getusecmapname(cmap);
if (usecmapname)
@@ -503,7 +504,7 @@ cleanup:
if (cmap)
fz_dropcmap(cmap);
if (file)
- fz_closefile(file);
+ fz_dropstream(file);
return error;
}
diff --git a/mupdf/pdf_function.c b/mupdf/pdf_function.c
index d6279ef4..fd241e7c 100644
--- a/mupdf/pdf_function.c
+++ b/mupdf/pdf_function.c
@@ -358,7 +358,7 @@ resizecode(pdf_function *func, int newsize)
}
static fz_error *
-parsecode(pdf_function *func, fz_file *stream, int *codeptr)
+parsecode(pdf_function *func, fz_stream *stream, int *codeptr)
{
fz_error *error = nil;
char buf[64];
@@ -488,14 +488,15 @@ static fz_error *
loadpostscriptfunc(pdf_function *func, pdf_xref *xref, fz_obj *dict, int oid, int gen)
{
fz_error *error = nil;
+ fz_stream *stream;
int codeptr;
pdf_logrsrc("load postscript function %d %d\n", oid, gen);
- error = pdf_openstream(xref, oid, gen);
+ error = pdf_openstream(&stream, xref, oid, gen);
if (error) goto cleanup;
- if (fz_readbyte(xref->stream) != '{')
+ if (fz_readbyte(stream) != '{')
goto cleanup;
func->u.p.code = nil;
@@ -503,15 +504,15 @@ loadpostscriptfunc(pdf_function *func, pdf_xref *xref, fz_obj *dict, int oid, in
codeptr = 0;
- error = parsecode(func, xref->stream, &codeptr);
+ error = parsecode(func, stream, &codeptr);
if (error) goto cleanup;
- pdf_closestream(xref);
+ fz_dropstream(stream);
return nil;
cleanup:
- pdf_closestream(xref);
+ fz_dropstream(stream);
if (error) return error;
return fz_throw("syntaxerror: postscript calculator");
}
@@ -910,6 +911,7 @@ static fz_error *
loadsamplefunc(pdf_function *func, pdf_xref *xref, fz_obj *dict, int oid, int gen)
{
fz_error *error = nil;
+ fz_stream *stream;
fz_obj *obj;
int samplecount;
int bps;
@@ -990,7 +992,7 @@ loadsamplefunc(pdf_function *func, pdf_xref *xref, fz_obj *dict, int oid, int ge
goto cleanup0;
}
- error = pdf_openstream(xref, oid, gen);
+ error = pdf_openstream(&stream, xref, oid, gen);
if (error)
goto cleanup0;
@@ -1003,29 +1005,29 @@ loadsamplefunc(pdf_function *func, pdf_xref *xref, fz_obj *dict, int oid, int ge
for (i = 0; i < samplecount; ++i)
{
- if (fz_peekbyte(xref->stream) == EOF)
+ if (fz_peekbyte(stream) == EOF)
{
error = fz_throw("syntaxerror: too few samples in function");
goto cleanup1;
}
if (bps == 8) {
- s = fz_readbyte(xref->stream);
+ s = fz_readbyte(stream);
}
else if (samplecount == 16) {
- s = fz_readbyte(xref->stream);
- s = (s << 8) + fz_readbyte(xref->stream);
+ s = fz_readbyte(stream);
+ s = (s << 8) + fz_readbyte(stream);
}
else if (samplecount == 32) {
- s = fz_readbyte(xref->stream);
- s = (s << 8) + fz_readbyte(xref->stream);
- s = (s << 8) + fz_readbyte(xref->stream);
- s = (s << 8) + fz_readbyte(xref->stream);
+ s = fz_readbyte(stream);
+ s = (s << 8) + fz_readbyte(stream);
+ s = (s << 8) + fz_readbyte(stream);
+ s = (s << 8) + fz_readbyte(stream);
}
else {
while (bits < bps)
{
- buf = (buf << 8) | (fz_readbyte(xref->stream) & 0xff);
+ buf = (buf << 8) | (fz_readbyte(stream) & 0xff);
bits += 8;
}
s = (buf >> (bits - bps)) & bitmask;
@@ -1033,21 +1035,17 @@ loadsamplefunc(pdf_function *func, pdf_xref *xref, fz_obj *dict, int oid, int ge
}
func->u.sa.samples[i] = s;
-
- error = fz_ferror(xref->stream);
- if (error)
- goto cleanup1;
}
}
- pdf_closestream(xref);
+ fz_dropstream(stream);
pdf_logrsrc("}\n");
return nil;
cleanup1:
- pdf_closestream(xref);
+ fz_dropstream(stream);
cleanup0:
if (error) return error;
return fz_throw("syntaxerror: sample function");
diff --git a/mupdf/pdf_image.c b/mupdf/pdf_image.c
index 4fd6643c..cd7457a0 100644
--- a/mupdf/pdf_image.c
+++ b/mupdf/pdf_image.c
@@ -1,5 +1,9 @@
-#include <fitz.h>
-#include <mupdf.h>
+/*
+ * TODO: this needs serious cleaning up, and error checking.
+ */
+
+#include "fitz.h"
+#include "mupdf.h"
void pdf_dropimage(fz_image *fzimg)
{
@@ -10,7 +14,8 @@ void pdf_dropimage(fz_image *fzimg)
}
fz_error *
-pdf_loadinlineimage(pdf_image **imgp, pdf_xref *xref, fz_obj *rdb, fz_obj *dict, fz_file *file)
+pdf_loadinlineimage(pdf_image **imgp, pdf_xref *xref,
+ fz_obj *rdb, fz_obj *dict, fz_stream *file)
{
fz_error *error;
pdf_image *img;
@@ -120,19 +125,22 @@ pdf_loadinlineimage(pdf_image **imgp, pdf_xref *xref, fz_obj *rdb, fz_obj *dict,
f = fz_dictgetsa(dict, "Filter", "F");
if (f)
{
- error = pdf_decodefilter(&filter, dict);
- if (error)
- return error;
+ fz_stream *tempfile;
- error = fz_pushfilter(file, filter);
+ error = pdf_buildinlinefilter(&filter, dict);
if (error)
return error;
- error = fz_readfile(&img->samples, file);
+ error = fz_openrfilter(&tempfile, filter, file);
if (error)
return error;
- fz_popfilter(file);
+ i = fz_readall(&img->samples, tempfile);
+ if (i < 0)
+ return fz_throw("ioerror: readall failed");
+
+ fz_dropfilter(filter);
+ fz_dropstream(tempfile);
}
else
{
@@ -141,9 +149,8 @@ pdf_loadinlineimage(pdf_image **imgp, pdf_xref *xref, fz_obj *rdb, fz_obj *dict,
return error;
i = fz_read(file, img->samples->bp, img->super.h * img->stride);
- error = fz_ferror(file);
- if (error)
- return error;
+ if (i < 0)
+ return fz_throw("ioerror: read failed");
img->samples->wp += img->super.h * img->stride;
}
diff --git a/mupdf/pdf_interpret.c b/mupdf/pdf_interpret.c
index d4b2b2be..e5ecf8ee 100644
--- a/mupdf/pdf_interpret.c
+++ b/mupdf/pdf_interpret.c
@@ -128,7 +128,7 @@ runxobject(pdf_csi *csi, pdf_xref *xref, pdf_xobject *xobj)
{
fz_error *error;
fz_node *transform;
- fz_file *file;
+ fz_stream *file;
/* gsave */
error = gsave(csi);
@@ -152,13 +152,13 @@ runxobject(pdf_csi *csi, pdf_xref *xref, pdf_xobject *xobj)
xobj->contents->rp = xobj->contents->bp;
- error = fz_openbuffer(&file, xobj->contents, FZ_READ);
+ error = fz_openrbuffer(&file, xobj->contents);
if (error)
return error;
error = pdf_runcsi(csi, xref, xobj->resources, file);
- fz_closefile(file);
+ fz_dropstream(file);
if (error)
return error;
@@ -176,7 +176,7 @@ runxobject(pdf_csi *csi, pdf_xref *xref, pdf_xobject *xobj)
*/
static fz_error *
-runinlineimage(pdf_csi *csi, pdf_xref *xref, fz_obj *rdb, fz_file *file, fz_obj *dict)
+runinlineimage(pdf_csi *csi, pdf_xref *xref, fz_obj *rdb, fz_stream *file, fz_obj *dict)
{
fz_error *error;
pdf_image *img;
@@ -1080,7 +1080,7 @@ syntaxerror:
}
fz_error *
-pdf_runcsi(pdf_csi *csi, pdf_xref *xref, fz_obj *rdb, fz_file *file)
+pdf_runcsi(pdf_csi *csi, pdf_xref *xref, fz_obj *rdb, fz_stream *file)
{
fz_error *error;
char buf[65536];
diff --git a/mupdf/pdf_lex.c b/mupdf/pdf_lex.c
index 36e7f50a..c1f9643f 100644
--- a/mupdf/pdf_lex.c
+++ b/mupdf/pdf_lex.c
@@ -50,7 +50,7 @@ static inline int fromhex(int ch)
}
static inline void
-lexwhite(fz_file *f)
+lexwhite(fz_stream *f)
{
int c;
while (1)
@@ -63,7 +63,7 @@ lexwhite(fz_file *f)
}
static inline void
-lexcomment(fz_file *f)
+lexcomment(fz_stream *f)
{
int c;
while (1)
@@ -76,7 +76,7 @@ lexcomment(fz_file *f)
}
static void
-lexnumber(fz_file *f, unsigned char *s, int n)
+lexnumber(fz_stream *f, unsigned char *s, int n)
{
while (n > 1)
{
@@ -89,7 +89,7 @@ lexnumber(fz_file *f, unsigned char *s, int n)
}
static void
-lexname(fz_file *f, unsigned char *s, int n)
+lexname(fz_stream *f, unsigned char *s, int n)
{
#if 0
unsigned char *p = s;
@@ -121,7 +121,7 @@ lexname(fz_file *f, unsigned char *s, int n)
}
static int
-lexstring(fz_file *f, unsigned char *buf, int n)
+lexstring(fz_stream *f, unsigned char *buf, int n)
{
unsigned char *s = buf;
unsigned char *e = buf + n;
@@ -194,7 +194,7 @@ lexstring(fz_file *f, unsigned char *buf, int n)
}
static int
-lexhexstring(fz_file *f, unsigned char *buf, int n)
+lexhexstring(fz_stream *f, unsigned char *buf, int n)
{
unsigned char *s = buf;
unsigned char *e = buf + n;
@@ -249,7 +249,7 @@ tokenfromkeyword(char *key)
}
int
-pdf_lex(fz_file *f, unsigned char *buf, int n, int *sl)
+pdf_lex(fz_stream *f, unsigned char *buf, int n, int *sl)
{
int c;
diff --git a/mupdf/pdf_open.c b/mupdf/pdf_open.c
index 34caa862..67d9b5d9 100644
--- a/mupdf/pdf_open.c
+++ b/mupdf/pdf_open.c
@@ -19,7 +19,7 @@ loadversion(pdf_xref *xref)
n = fz_seek(xref->file, 0, 0);
if (n < 0)
- return fz_ferror(xref->file);
+ return fz_throw("ioerror: seek failed");
fz_readline(xref->file, buf, sizeof buf);
if (memcmp(buf, "%PDF-", 5) != 0)
@@ -41,15 +41,15 @@ readstartxref(pdf_xref *xref)
t = fz_seek(xref->file, 0, 2);
if (t == -1)
- return fz_ferror(xref->file);
+ return fz_throw("ioerror: seek failed");
t = fz_seek(xref->file, MAX(0, t - ((int)sizeof buf)), 0);
if (t == -1)
- return fz_ferror(xref->file);
+ return fz_throw("ioerror: seek failed");
n = fz_read(xref->file, buf, sizeof buf);
if (n == -1)
- return fz_ferror(xref->file);
+ return fz_throw("ioerror: read failed");
for (i = n - 9; i >= 0; i--)
{
@@ -83,7 +83,7 @@ readoldtrailer(pdf_xref *xref, char *buf, int cap)
fz_readline(xref->file, buf, cap);
if (strcmp(buf, "xref") != 0)
- return fz_throw("syntaxerror: missing xref");
+ return fz_throw("ioerror: missing xref");
while (1)
{
@@ -92,7 +92,8 @@ readoldtrailer(pdf_xref *xref, char *buf, int cap)
break;
n = fz_readline(xref->file, buf, cap);
- if (n < 0) return fz_ferror(xref->file);
+ if (n < 0)
+ return fz_throw("ioerror: read failed");
s = buf;
ofs = atoi(strsep(&s, " "));
@@ -103,10 +104,12 @@ readoldtrailer(pdf_xref *xref, char *buf, int cap)
fz_seek(xref->file, -(n + buf - s + 2), 1);
t = fz_tell(xref->file);
- if (t < 0) return fz_ferror(xref->file);
+ if (t < 0)
+ return fz_throw("ioerror: tell failed");
n = fz_seek(xref->file, t + 20 * len, 0);
- if (n < 0) return fz_ferror(xref->file);
+ if (n < 0)
+ return fz_throw("ioerror: seek failed");
}
t = pdf_lex(xref->file, buf, cap, &n);
@@ -135,7 +138,7 @@ readtrailer(pdf_xref *xref, char *buf, int cap)
n = fz_seek(xref->file, xref->startxref, 0);
if (n < 0)
- return fz_ferror(xref->file);
+ return fz_throw("ioerror: seek failed");
c = fz_peekbyte(xref->file);
if (c == 'x')
@@ -173,7 +176,8 @@ readoldxref(fz_obj **trailerp, pdf_xref *xref, char *buf, int cap)
break;
n = fz_readline(xref->file, buf, cap);
- if (n < 0) return fz_ferror(xref->file);
+ if (n < 0)
+ return fz_throw("ioerror: read failed");
s = buf;
ofs = atoi(strsep(&s, " "));
@@ -189,8 +193,10 @@ readoldxref(fz_obj **trailerp, pdf_xref *xref, char *buf, int cap)
for (i = 0; i < len; i++)
{
n = fz_read(xref->file, buf, 20);
- if (n < 0) return fz_ferror(xref->file);
- if (n != 20) return fz_throw("syntaxerror: truncated xref table");
+ if (n < 0)
+ return fz_throw("ioerror: read failed");
+ if (n != 20)
+ return fz_throw("syntaxerror: truncated xref table");
if (!xref->table[ofs + i].type)
{
s = buf;
@@ -215,6 +221,7 @@ static fz_error *
readnewxref(fz_obj **trailerp, pdf_xref *xref, char *buf, int cap)
{
fz_error *error;
+ fz_stream *stm;
fz_obj *trailer;
fz_obj *obj;
int oid, gen, stmofs;
@@ -268,7 +275,7 @@ readnewxref(fz_obj **trailerp, pdf_xref *xref, char *buf, int cap)
goto cleanup;
}
- error = pdf_openstream(xref, oid, gen);
+ error = pdf_openstream(&stm, xref, oid, gen);
if (error)
goto cleanup;
@@ -278,21 +285,19 @@ readnewxref(fz_obj **trailerp, pdf_xref *xref, char *buf, int cap)
int b = 0;
int c = 0;
- if (fz_peekbyte(xref->stream) == EOF)
+ if (fz_peekbyte(stm) == EOF)
{
- error = fz_ferror(xref->stream);
- if (!error)
- error = fz_throw("syntaxerror: truncated xref stream");
- pdf_closestream(xref);
+ error = fz_throw("syntaxerror: truncated xref stream");
+ fz_dropstream(stm);
goto cleanup;
}
for (n = 0; n < w0; n++)
- a = (a << 8) + fz_readbyte(xref->stream);
+ a = (a << 8) + fz_readbyte(stm);
for (n = 0; n < w1; n++)
- b = (b << 8) + fz_readbyte(xref->stream);
+ b = (b << 8) + fz_readbyte(stm);
for (n = 0; n < w2; n++)
- c = (c << 8) + fz_readbyte(xref->stream);
+ c = (c << 8) + fz_readbyte(stm);
if (!xref->table[i].type)
{
@@ -303,7 +308,7 @@ readnewxref(fz_obj **trailerp, pdf_xref *xref, char *buf, int cap)
}
}
- pdf_closestream(xref);
+ fz_dropstream(stm);
*trailerp = trailer;
@@ -322,7 +327,7 @@ readxref(fz_obj **trailerp, pdf_xref *xref, int ofs, char *buf, int cap)
n = fz_seek(xref->file, ofs, 0);
if (n < 0)
- return fz_ferror(xref->file);
+ return fz_throw("ioerror: seek failed");
c = fz_peekbyte(xref->file);
if (c == 'x')
@@ -380,6 +385,7 @@ fz_error *
pdf_loadobjstm(pdf_xref *xref, int oid, int gen, char *buf, int cap)
{
fz_error *error;
+ fz_stream *stm;
fz_obj *objstm;
int *oidbuf;
int *ofsbuf;
@@ -401,53 +407,53 @@ pdf_loadobjstm(pdf_xref *xref, int oid, int gen, char *buf, int cap)
pdf_logxref(" count %d\n", count);
oidbuf = fz_malloc(count * sizeof(int));
- if (!oidbuf) { error = fz_outofmem; goto cleanup1; }
+ if (!oidbuf) { error = fz_outofmem; goto cleanupobj; }
ofsbuf = fz_malloc(count * sizeof(int));
- if (!ofsbuf) { error = fz_outofmem; goto cleanup2; }
+ if (!ofsbuf) { error = fz_outofmem; goto cleanupoid; }
- error = pdf_openstream(xref, oid, gen);
+ error = pdf_openstream(&stm, xref, oid, gen);
if (error)
- goto cleanup3;
+ goto cleanupofs;
for (i = 0; i < count; i++)
{
- t = pdf_lex(xref->stream, buf, cap, &n);
+ t = pdf_lex(stm, buf, cap, &n);
if (t != PDF_TINT)
{
error = fz_throw("syntaxerror: corrupt object stream");
- goto cleanup4;
+ goto cleanupstm;
}
oidbuf[i] = atoi(buf);
- t = pdf_lex(xref->stream, buf, cap, &n);
+ t = pdf_lex(stm, buf, cap, &n);
if (t != PDF_TINT)
{
error = fz_throw("syntaxerror: corrupt object stream");
- goto cleanup4;
+ goto cleanupstm;
}
ofsbuf[i] = atoi(buf);
}
- n = fz_seek(xref->stream, first, 0);
+ n = fz_seek(stm, first, 0);
if (n < 0)
{
- error = fz_ferror(xref->stream);
- goto cleanup4;
+ error = fz_throw("ioerror: seek failed");
+ goto cleanupstm;
}
for (i = 0; i < count; i++)
{
/* FIXME: seek to first + ofsbuf[i] */
- error = pdf_parsestmobj(&obj, xref->stream, buf, cap);
+ error = pdf_parsestmobj(&obj, stm, buf, cap);
if (error)
- goto cleanup4;
+ goto cleanupstm;
if (oidbuf[i] < 1 || oidbuf[i] >= xref->len)
{
error = fz_throw("rangecheck: object number out of range");
- goto cleanup4;
+ goto cleanupstm;
}
if (xref->table[oidbuf[i]].obj)
@@ -455,19 +461,19 @@ pdf_loadobjstm(pdf_xref *xref, int oid, int gen, char *buf, int cap)
xref->table[oidbuf[i]].obj = obj;
}
- pdf_closestream(xref);
+ fz_dropstream(stm);
fz_free(ofsbuf);
fz_free(oidbuf);
fz_dropobj(objstm);
return nil;
-cleanup4:
- pdf_closestream(xref);
-cleanup3:
+cleanupstm:
+ fz_dropstream(stm);
+cleanupofs:
fz_free(ofsbuf);
-cleanup2:
+cleanupoid:
fz_free(oidbuf);
-cleanup1:
+cleanupobj:
fz_dropobj(objstm);
return error;
}
@@ -487,7 +493,7 @@ pdf_loadxref(pdf_xref *xref, char *filename)
pdf_logxref("loadxref '%s' %p\n", filename, xref);
- error = fz_openfile(&xref->file, filename, FZ_READ);
+ error = fz_openrfile(&xref->file, filename);
if (error)
return error;
diff --git a/mupdf/pdf_page.c b/mupdf/pdf_page.c
index b230c871..44ac769c 100644
--- a/mupdf/pdf_page.c
+++ b/mupdf/pdf_page.c
@@ -5,16 +5,17 @@ static fz_error *
runone(pdf_csi *csi, pdf_xref *xref, fz_obj *rdb, fz_obj *stmref)
{
fz_error *error;
+ fz_stream *stm;
pdf_logpage("simple content stream\n");
- error = pdf_openstream(xref, fz_tonum(stmref), fz_togen(stmref));
+ error = pdf_openstream(&stm, xref, fz_tonum(stmref), fz_togen(stmref));
if (error)
return error;
- error = pdf_runcsi(csi, xref, rdb, xref->stream);
+ error = pdf_runcsi(csi, xref, rdb, stm);
- pdf_closestream(xref);
+ fz_dropstream(stm);
return error;
}
@@ -26,7 +27,7 @@ static fz_error *
runmany(pdf_csi *csi, pdf_xref *xref, fz_obj *rdb, fz_obj *list)
{
fz_error *error;
- fz_file *file;
+ fz_stream *file;
fz_buffer *big;
fz_buffer *one;
fz_obj *stm;
@@ -39,12 +40,14 @@ runmany(pdf_csi *csi, pdf_xref *xref, fz_obj *rdb, fz_obj *list)
if (error)
return error;
- error = fz_openbuffer(&file, big, FZ_WRITE);
+ error = fz_openwbuffer(&file, big);
if (error)
goto cleanup0;
for (i = 0; i < fz_arraylen(list); i++)
{
+ /* TODO dont use loadstream here */
+
stm = fz_arrayget(list, i);
error = pdf_loadstream(&one, xref, fz_tonum(stm), fz_togen(stm));
if (error)
@@ -56,33 +59,28 @@ runmany(pdf_csi *csi, pdf_xref *xref, fz_obj *rdb, fz_obj *list)
if (n == -1)
{
- error = fz_ferror(file);
+ error = fz_throw("ioerror: write failed");
goto cleanup1;
}
- n = fz_printstring(file, " ");
- if (n == -1)
- {
- error = fz_ferror(file);
- goto cleanup1;
- }
+ fz_printstr(file, " ");
}
- fz_closefile(file);
+ fz_dropstream(file);
- error = fz_openbuffer(&file, big, FZ_READ);
+ error = fz_openrbuffer(&file, big);
if (error)
goto cleanup0;
error = pdf_runcsi(csi, xref, rdb, file);
- fz_closefile(file);
+ fz_dropstream(file);
fz_dropbuffer(big);
return error;
cleanup1:
- fz_closefile(file);
+ fz_dropstream(file);
cleanup0:
fz_dropbuffer(big);
return error;
diff --git a/mupdf/pdf_parse.c b/mupdf/pdf_parse.c
index e30bb3a2..8b091d67 100644
--- a/mupdf/pdf_parse.c
+++ b/mupdf/pdf_parse.c
@@ -107,7 +107,7 @@ pdf_toucs2(unsigned short **dstp, fz_obj *src)
}
fz_error *
-pdf_parsearray(fz_obj **op, fz_file *file, char *buf, int cap)
+pdf_parsearray(fz_obj **op, fz_stream *file, char *buf, int cap)
{
fz_error *error = nil;
fz_obj *ary = nil;
@@ -206,7 +206,7 @@ cleanup:
}
fz_error *
-pdf_parsedict(fz_obj **op, fz_file *file, char *buf, int cap)
+pdf_parsedict(fz_obj **op, fz_stream *file, char *buf, int cap)
{
fz_error *error = nil;
fz_obj *dict = nil;
@@ -298,7 +298,7 @@ cleanup:
}
fz_error *
-pdf_parsestmobj(fz_obj **op, fz_file *file, char *buf, int cap)
+pdf_parsestmobj(fz_obj **op, fz_stream *file, char *buf, int cap)
{
int tok, len;
@@ -321,7 +321,7 @@ pdf_parsestmobj(fz_obj **op, fz_file *file, char *buf, int cap)
}
fz_error *
-pdf_parseindobj(fz_obj **op, fz_file *file, char *buf, int cap,
+pdf_parseindobj(fz_obj **op, fz_stream *file, char *buf, int cap,
int *ooid, int *ogid, int *ostmofs)
{
fz_error *error = nil;
diff --git a/mupdf/pdf_pattern.c b/mupdf/pdf_pattern.c
index d4e99c48..8b9e9bc4 100644
--- a/mupdf/pdf_pattern.c
+++ b/mupdf/pdf_pattern.c
@@ -24,6 +24,7 @@ pdf_loadpattern(pdf_pattern **patp, pdf_xref *xref, fz_obj *dict, fz_obj *stmref
{
fz_error *error;
pdf_pattern *pat;
+ fz_stream *stm;
fz_obj *resources;
fz_obj *obj;
pdf_csi *csi;
@@ -98,13 +99,13 @@ pdf_loadpattern(pdf_pattern **patp, pdf_xref *xref, fz_obj *dict, fz_obj *stmref
if (error)
goto cleanup;
- error = pdf_openstream(xref, fz_tonum(stmref), fz_togen(stmref));
+ error = pdf_openstream(&stm, xref, fz_tonum(stmref), fz_togen(stmref));
if (error)
goto cleanup2;
- error = pdf_runcsi(csi, xref, resources, xref->stream);
+ error = pdf_runcsi(csi, xref, resources, stm);
- pdf_closestream(xref);
+ fz_dropstream(stm);
if (error)
goto cleanup2;
diff --git a/mupdf/pdf_repair.c b/mupdf/pdf_repair.c
index e533d826..6fcbde63 100644
--- a/mupdf/pdf_repair.c
+++ b/mupdf/pdf_repair.c
@@ -15,7 +15,7 @@ struct entry
};
static fz_error *
-parseobj(fz_file *file, char *buf, int cap, int *stmofs, int *stmlen,
+parseobj(fz_stream *file, char *buf, int cap, int *stmofs, int *stmlen,
int *isroot, int *isinfo)
{
fz_error *error;
@@ -108,7 +108,7 @@ fz_error *
pdf_repairxref(pdf_xref *xref, char *filename)
{
fz_error *error;
- fz_file *file;
+ fz_stream *file;
struct entry *list = nil;
int listlen;
@@ -127,7 +127,7 @@ pdf_repairxref(pdf_xref *xref, char *filename)
int next;
int i;
- error = fz_openfile(&file, filename, FZ_READ);
+ error = fz_openrfile(&file, filename);
if (error)
return error;
@@ -295,7 +295,7 @@ pdf_repairxref(pdf_xref *xref, char *filename)
return nil;
cleanup:
- fz_closefile(file);
+ fz_dropstream(file);
fz_free(list);
return error;
}
diff --git a/mupdf/pdf_save.c b/mupdf/pdf_save.c
index 344d942c..a23fa419 100644
--- a/mupdf/pdf_save.c
+++ b/mupdf/pdf_save.c
@@ -1,12 +1,14 @@
#include <fitz.h>
#include <mupdf.h>
-#define TIGHT 0
+#define TIGHT 1
static fz_error *
-writestream(fz_file *out, pdf_xref *xref, pdf_crypt *encrypt, int oid, int gen)
+writestream(fz_stream *out, pdf_xref *xref, pdf_crypt *encrypt, int oid, int gen)
{
fz_error *error;
+ fz_stream *dststm;
+ fz_stream *srcstm;
unsigned char buf[4096];
fz_filter *ef;
int n;
@@ -19,47 +21,55 @@ writestream(fz_file *out, pdf_xref *xref, pdf_crypt *encrypt, int oid, int gen)
if (error)
return error;
- error = fz_pushfilter(out, ef);
+ error = fz_openrfilter(&dststm, ef, out);
fz_dropfilter(ef);
if (error)
return error;
}
+ else
+ {
+ dststm = fz_keepstream(out);
+ }
- error = pdf_openrawstream(xref, oid, gen);
+ error = pdf_openrawstream(&srcstm, xref, oid, gen);
if (error)
- goto cleanup;
+ goto cleanupdst;
while (1)
{
- n = fz_read(xref->stream, buf, sizeof buf);
+ n = fz_read(srcstm, buf, sizeof buf);
if (n == 0)
break;
if (n < 0)
{
- error = fz_ferror(xref->stream);
- pdf_closestream(xref);
- goto cleanup;
+ error = fz_throw("ioerror: read failed");
+ goto cleanupsrc;
+ }
+
+ n = fz_write(dststm, buf, n);
+ if (n < 0)
+ {
+ error = fz_throw("ioerror: write failed");
+ goto cleanupsrc;
}
- fz_write(out, buf, n);
}
- pdf_closestream(xref);
-
- if (encrypt)
- fz_popfilter(out);
+ fz_dropstream(srcstm);
+ fz_dropstream(dststm);
fz_print(out, "endstream\n");
return nil;
-cleanup:
- if (encrypt)
- fz_popfilter(out);
+cleanupsrc:
+ fz_dropstream(srcstm);
+cleanupdst:
+ fz_dropstream(dststm);
return error;
}
static fz_error *
-writeobject(fz_file *out, pdf_xref *xref, pdf_crypt *encrypt, int oid, int gen)
+writeobject(fz_stream *out, pdf_xref *xref, pdf_crypt *encrypt, int oid, int gen)
{
pdf_xrefentry *x = xref->table + oid;
fz_error *error;
@@ -87,10 +97,6 @@ writeobject(fz_file *out, pdf_xref *xref, pdf_crypt *encrypt, int oid, int gen)
fz_print(out, "endobj\n\n");
- error = fz_ferror(out);
- if (error)
- return error;
-
return nil;
}
@@ -107,7 +113,7 @@ fz_error *
pdf_updatexref(pdf_xref *xref, char *path)
{
fz_error *error;
- fz_file *out;
+ fz_stream *out;
int oid;
int i, n;
int startxref;
@@ -115,7 +121,7 @@ pdf_updatexref(pdf_xref *xref, char *path)
pdf_logxref("updatexref '%s' %p\n", path, xref);
- error = fz_openfile(&out, path, FZ_APPEND);
+ error = fz_openafile(&out, path);
if (error)
return error;
@@ -198,11 +204,11 @@ pdf_updatexref(pdf_xref *xref, char *path)
xref->startxref = startxref;
- fz_closefile(out);
+ fz_dropstream(out);
return nil;
cleanup:
- fz_closefile(out);
+ fz_dropstream(out);
return error;
}
@@ -210,7 +216,7 @@ fz_error *
pdf_savexref(pdf_xref *xref, char *path, pdf_crypt *encrypt)
{
fz_error *error;
- fz_file *out;
+ fz_stream *out;
int oid;
int startxref;
int *ofsbuf;
@@ -239,7 +245,7 @@ pdf_savexref(pdf_xref *xref, char *path, pdf_crypt *encrypt)
if (!ofsbuf)
return fz_outofmem;
- error = fz_openfile(&out, path, FZ_WRITE);
+ error = fz_openwfile(&out, path);
if (error)
{
fz_free(ofsbuf);
@@ -309,12 +315,12 @@ pdf_savexref(pdf_xref *xref, char *path, pdf_crypt *encrypt)
xref->startxref = startxref;
if(ofsbuf) fz_free(ofsbuf);
- fz_closefile(out);
+ fz_dropstream(out);
return nil;
cleanup:
if(ofsbuf) fz_free(ofsbuf);
- fz_closefile(out);
+ fz_dropstream(out);
return error;
}
diff --git a/mupdf/pdf_shade4.c b/mupdf/pdf_shade4.c
index 8454643f..ddd42efd 100644
--- a/mupdf/pdf_shade4.c
+++ b/mupdf/pdf_shade4.c
@@ -164,7 +164,7 @@ cleanup:
}
static int
-getdata(fz_file *stream, int bps)
+getdata(fz_stream *stream, int bps)
{
unsigned int bitmask = (1 << bps) - 1;
unsigned int buf = 0;
@@ -188,6 +188,7 @@ fz_error *
pdf_loadtype5shade(fz_shade *shade, pdf_xref *xref, fz_obj *shading, fz_obj *ref)
{
fz_error *error;
+ fz_stream *stream;
fz_obj *obj;
int bpcoord;
@@ -256,31 +257,29 @@ pdf_loadtype5shade(fz_shade *shade, pdf_xref *xref, fz_obj *shading, fz_obj *ref
}
q = 0;
- error = pdf_openstream(xref, fz_tonum(ref), fz_togen(ref));
+ error = pdf_openstream(&stream, xref, fz_tonum(ref), fz_togen(ref));
if (error) goto cleanup;
- while (fz_peekbyte(xref->stream) != EOF)
+ while (fz_peekbyte(stream) != EOF)
{
for (p = 0; p < vpr; ++p) {
int idx;
idx = q * vpr + p;
- t = getdata(xref->stream, bpcoord);
+ t = getdata(stream, bpcoord);
x[idx] = x0 + (t * (x1 - x0) / ((float)pow(2, bpcoord) - 1));
- t = getdata(xref->stream, bpcoord);
+ t = getdata(stream, bpcoord);
y[idx] = y0 + (t * (y1 - y0) / ((float)pow(2, bpcoord) - 1));
for (i=0; i < ncomp; ++i) {
- t = getdata(xref->stream, bpcomp);
+ t = getdata(stream, bpcomp);
c[i][idx] = c0[i] + (t * (c1[i] - c0[i]) / (float)(pow(2, bpcomp) - 1));
}
}
q++;
}
- if ((error = fz_ferror(xref->stream)))
- goto cleanup;
- pdf_closestream(xref);
+ fz_dropstream(stream);
#define ADD_VERTEX(idx) \
{\
@@ -564,6 +563,7 @@ fz_error *
pdf_loadtype6shade(fz_shade *shade, pdf_xref *xref, fz_obj *shading, fz_obj *ref)
{
fz_error *error;
+ fz_stream *stream;
fz_obj *obj;
int bpcoord;
@@ -626,24 +626,24 @@ pdf_loadtype6shade(fz_shade *shade, pdf_xref *xref, fz_obj *shading, fz_obj *ref
n = 2 + shade->cs->n;
j = 0;
- error = pdf_openstream(xref, fz_tonum(ref), fz_togen(ref));
+ error = pdf_openstream(&stream, xref, fz_tonum(ref), fz_togen(ref));
if (error) goto cleanup;
- while (fz_peekbyte(xref->stream) != EOF)
+ while (fz_peekbyte(stream) != EOF)
{
- flag = getdata(xref->stream, bpflag);
+ flag = getdata(stream, bpflag);
for (i = 0; i < 12; ++i) {
- t = getdata(xref->stream, bpcoord);
+ t = getdata(stream, bpcoord);
p[i].x = (float)(p0.x + (t * (p1.x - p0.x) / (pow(2, bpcoord) - 1.)));
- t = getdata(xref->stream, bpcoord);
+ t = getdata(stream, bpcoord);
p[i].y = (float)(p0.y + (t * (p1.y - p0.y) / (pow(2, bpcoord) - 1.)));
}
for (i = 0; i < 4; ++i) {
int k;
for (k=0; k < ncomp; ++k) {
- t = getdata(xref->stream, bpcomp);
+ t = getdata(stream, bpcomp);
patch.color[i][k] =
c0[k] + (t * (c1[k] - c0[k]) / (pow(2, bpcomp) - 1.0f));
}
@@ -665,10 +665,8 @@ pdf_loadtype6shade(fz_shade *shade, pdf_xref *xref, fz_obj *shading, fz_obj *ref
j = drawpatch(patch, shade, j, ncomp, 0);
}
- if ((error = fz_ferror(xref->stream)) )
- goto cleanup;
- pdf_closestream(xref);
+ fz_dropstream(stream);
shade->meshlen = j / n / 3;
@@ -681,6 +679,7 @@ fz_error *
pdf_loadtype7shade(fz_shade *shade, pdf_xref *xref, fz_obj *shading, fz_obj *ref)
{
fz_error *error;
+ fz_stream *stream;
fz_obj *obj;
int bpcoord;
@@ -742,24 +741,24 @@ pdf_loadtype7shade(fz_shade *shade, pdf_xref *xref, fz_obj *shading, fz_obj *ref
n = 2 + shade->cs->n;
j = 0;
- error = pdf_openstream(xref, fz_tonum(ref), fz_togen(ref));
+ error = pdf_openstream(&stream, xref, fz_tonum(ref), fz_togen(ref));
if (error) goto cleanup;
- while (fz_peekbyte(xref->stream) != EOF)
+ while (fz_peekbyte(stream) != EOF)
{
- flag = getdata(xref->stream, bpflag);
+ flag = getdata(stream, bpflag);
for (i = 0; i < 16; ++i) {
- t = getdata(xref->stream, bpcoord);
+ t = getdata(stream, bpcoord);
p[i].x = x0 + (t * (x1 - x0) / (pow(2, bpcoord) - 1.));
- t = getdata(xref->stream, bpcoord);
+ t = getdata(stream, bpcoord);
p[i].y = y0 + (t * (y1 - y0) / (pow(2, bpcoord) - 1.));
}
for (i = 0; i < 4; ++i) {
int k;
for (k=0; k < ncomp; ++k) {
- t = getdata(xref->stream, bpcomp);
+ t = getdata(stream, bpcomp);
patch.color[i][k] =
c0[k] + (t * (c1[k] - c0[k]) / (pow(2, bpcomp) - 1.0f));
}
@@ -784,10 +783,8 @@ pdf_loadtype7shade(fz_shade *shade, pdf_xref *xref, fz_obj *shading, fz_obj *ref
j = drawpatch(patch, shade, j, ncomp, 0);
}
- if ((error = fz_ferror(xref->stream)) )
- goto cleanup;
- pdf_closestream(xref);
+ fz_dropstream(stream);
shade->meshlen = j / n / 3;
diff --git a/mupdf/pdf_stream.c b/mupdf/pdf_stream.c
index 01958853..0479dfd7 100644
--- a/mupdf/pdf_stream.c
+++ b/mupdf/pdf_stream.c
@@ -1,5 +1,5 @@
-#include <fitz.h>
-#include <mupdf.h>
+#include "fitz.h"
+#include "mupdf.h"
/*
* Check if an object is a stream or not.
@@ -173,7 +173,7 @@ buildfilterchain(fz_filter **filterp, fz_filter *head, fz_obj *fs, fz_obj *ps)
* stream length, followed by a decryption filter.
*/
static fz_error *
-makerawfilter(fz_filter **filterp, pdf_xref *xref, fz_obj *stmobj, int oid, int gen)
+buildrawfilter(fz_filter **filterp, pdf_xref *xref, fz_obj *stmobj, int oid, int gen)
{
fz_error *error;
fz_filter *base;
@@ -224,7 +224,7 @@ makerawfilter(fz_filter **filterp, pdf_xref *xref, fz_obj *stmobj, int oid, int
* constraining to stream length, and without decryption.
*/
fz_error *
-pdf_decodefilter(fz_filter **filterp, fz_obj *stmobj)
+pdf_buildinlinefilter(fz_filter **filterp, fz_obj *stmobj)
{
fz_obj *filters;
fz_obj *params;
@@ -250,14 +250,14 @@ pdf_decodefilter(fz_filter **filterp, fz_obj *stmobj)
* to stream length and decrypting.
*/
static fz_error *
-makedecodefilter(fz_filter **filterp, pdf_xref *xref, fz_obj *stmobj, int oid, int gen)
+pdf_buildfilter(fz_filter **filterp, pdf_xref *xref, fz_obj *stmobj, int oid, int gen)
{
fz_error *error;
fz_filter *base, *pipe, *tmp;
fz_obj *filters;
fz_obj *params;
- error = makerawfilter(&base, xref, stmobj, oid, gen);
+ error = buildrawfilter(&base, xref, stmobj, oid, gen);
if (error)
return error;
@@ -321,11 +321,10 @@ cleanup0:
/*
* Open a stream for reading the raw (compressed but decrypted) data.
- * Put the opened file in xref->stream. Using xref->file while this
- * is open is a bad idea.
+ * Using xref->file while this is open is a bad idea.
*/
fz_error *
-pdf_openrawstream(pdf_xref *xref, int oid, int gen)
+pdf_openrawstream(fz_stream **stmp, pdf_xref *xref, int oid, int gen)
{
pdf_xrefentry *x;
fz_error *error;
@@ -343,12 +342,12 @@ pdf_openrawstream(pdf_xref *xref, int oid, int gen)
if (x->stmbuf)
{
- return fz_openbuffer(&xref->stream, x->stmbuf, FZ_READ);
+ return fz_openrbuffer(stmp, x->stmbuf);
}
if (x->stmofs)
{
- error = makerawfilter(&filter, xref, x->obj, oid, gen);
+ error = buildrawfilter(&filter, xref, x->obj, oid, gen);
if (error)
return error;
@@ -356,15 +355,16 @@ pdf_openrawstream(pdf_xref *xref, int oid, int gen)
if (n == -1)
{
fz_dropfilter(filter);
- return fz_ferror(xref->file);
+ return fz_throw("ioerror: seek failed");
}
- error = fz_pushfilter(xref->file, filter);
+ error = fz_openrfilter(stmp, filter, xref->file);
+
fz_dropfilter(filter);
+
if (error)
return error;
- xref->stream = xref->file;
return nil;
}
@@ -377,10 +377,11 @@ pdf_openrawstream(pdf_xref *xref, int oid, int gen)
* Using xref->file while a stream is open is a Bad idea.
*/
fz_error *
-pdf_openstream(pdf_xref *xref, int oid, int gen)
+pdf_openstream(fz_stream **stmp, pdf_xref *xref, int oid, int gen)
{
pdf_xrefentry *x;
fz_error *error;
+ fz_stream *rawstm;
fz_filter *filter;
int n;
@@ -395,25 +396,26 @@ pdf_openstream(pdf_xref *xref, int oid, int gen)
if (x->stmbuf)
{
- error = makedecodefilter(&filter, xref, x->obj, oid, gen);
+ error = pdf_buildfilter(&filter, xref, x->obj, oid, gen);
if (error)
return error;
- error = fz_openbuffer(&xref->stream, x->stmbuf, FZ_READ);
+ error = fz_openrbuffer(&rawstm, x->stmbuf);
if (error)
{
fz_dropfilter(filter);
return error;
}
- error = fz_pushfilter(xref->stream, filter);
+ error = fz_openrfilter(stmp, filter, rawstm);
fz_dropfilter(filter);
+ fz_dropstream(rawstm);
return error;
}
if (x->stmofs)
{
- error = makedecodefilter(&filter, xref, x->obj, oid, gen);
+ error = pdf_buildfilter(&filter, xref, x->obj, oid, gen);
if (error)
return error;
@@ -421,15 +423,14 @@ pdf_openstream(pdf_xref *xref, int oid, int gen)
if (n == -1)
{
fz_dropfilter(filter);
- return fz_ferror(xref->file);
+ return fz_throw("ioerror: seek failed");
}
- error = fz_pushfilter(xref->file, filter);
+ error = fz_openrfilter(stmp, filter, xref->file);
fz_dropfilter(filter);
if (error)
return error;
- xref->stream = xref->file;
return nil;
}
@@ -437,36 +438,26 @@ pdf_openstream(pdf_xref *xref, int oid, int gen)
}
/*
- * Close the xref->stream file opened by either
- * pdf_openrawstream or pdf_openstream.
- */
-void
-pdf_closestream(pdf_xref *xref)
-{
- if (xref->stream == xref->file)
- fz_popfilter(xref->file);
- else
- fz_closefile(xref->stream);
- xref->stream = nil;
-}
-
-/*
* Load raw (compressed but decrypted) contents of a stream into buf.
*/
fz_error *
pdf_loadrawstream(fz_buffer **bufp, pdf_xref *xref, int oid, int gen)
{
fz_error *error;
+ fz_stream *stm;
+ int n;
- error = pdf_openrawstream(xref, oid, gen);
+ error = pdf_openrawstream(&stm, xref, oid, gen);
if (error)
return error;
- error = fz_readfile(bufp, xref->stream);
+ n = fz_readall(bufp, stm);
- pdf_closestream(xref);
+ fz_dropstream(stm);
- return error;
+ if (n < 0)
+ return fz_throw("ioerror: readall failed");
+ return nil;
}
/*
@@ -476,15 +467,19 @@ fz_error *
pdf_loadstream(fz_buffer **bufp, pdf_xref *xref, int oid, int gen)
{
fz_error *error;
+ fz_stream *stm;
+ int n;
- error = pdf_openstream(xref, oid, gen);
+ error = pdf_openstream(&stm, xref, oid, gen);
if (error)
return error;
- error = fz_readfile(bufp, xref->stream);
+ n = fz_readall(bufp, stm);
- pdf_closestream(xref);
+ fz_dropstream(stm);
- return error;
+ if (n < 0)
+ return fz_throw("ioerror: readall failed");
+ return nil;
}
diff --git a/mupdf/pdf_type3.c b/mupdf/pdf_type3.c
index b1da3380..092db4de 100644
--- a/mupdf/pdf_type3.c
+++ b/mupdf/pdf_type3.c
@@ -66,16 +66,17 @@ loadcharproc(fz_tree **treep, pdf_xref *xref, fz_obj *rdb, fz_obj *stmref)
{
fz_error *error;
pdf_csi *csi;
+ fz_stream *stm;
error = pdf_newcsi(&csi, 1);
- error = pdf_openstream(xref, fz_tonum(stmref), fz_togen(stmref));
+ error = pdf_openstream(&stm, xref, fz_tonum(stmref), fz_togen(stmref));
if (error)
return error;
- error = pdf_runcsi(csi, xref, rdb, xref->stream);
+ error = pdf_runcsi(csi, xref, rdb, stm);
- pdf_closestream(xref);
+ fz_dropstream(stm);
*treep = csi->tree;
csi->tree = nil;
diff --git a/mupdf/pdf_xref.c b/mupdf/pdf_xref.c
index 7095850c..e4d25832 100644
--- a/mupdf/pdf_xref.c
+++ b/mupdf/pdf_xref.c
@@ -54,7 +54,7 @@ pdf_closexref(pdf_xref *xref)
}
if (xref->file)
- fz_closefile(xref->file);
+ fz_dropstream(xref->file);
if (xref->trailer)
fz_dropobj(xref->trailer);
@@ -389,7 +389,7 @@ pdf_cacheobject(pdf_xref *xref, int oid, int gen)
{
n = fz_seek(xref->file, x->ofs, 0);
if (n < 0)
- return fz_ferror(xref->file);
+ return fz_throw("ioerror: seek failed");
error = pdf_parseindobj(&x->obj, xref->file, buf, sizeof buf, &roid, &rgen, &x->stmofs);
if (error)
diff --git a/samus/sa_tiff.c b/samus/sa_tiff.c
index 3530f944..6a6db2d7 100644
--- a/samus/sa_tiff.c
+++ b/samus/sa_tiff.c
@@ -11,7 +11,7 @@ typedef struct sa_tiff_s sa_tiff;
struct sa_tiff_s
{
/* file and byte order */
- fz_file *file;
+ fz_stream *file;
unsigned order;
/* where we can find the strips of image data */
@@ -199,7 +199,7 @@ tiffreadstrips(sa_tiff *tiff)
fz_error *error;
fz_obj *params;
fz_buffer *buf;
- fz_file *file;
+ fz_stream *file;
fz_filter *filter;
unsigned char tmp[512];
@@ -264,17 +264,20 @@ printf("w=%d h=%d n=%d bpc=%d ",
/* TODO: scrap write-file and decode with filter directly to final destination */
error = fz_newbuffer(&buf, 4096);
- error = fz_openbuffer(&file, buf, FZ_WRITE);
+ error = fz_openwbuffer(&file, buf);
if (filter)
{
- error = fz_pushfilter(file, filter);
+ fz_stream *temp;
+ error = fz_openwfilter(&temp, filter, file);
if (error)
{
fz_dropfilter(filter);
- fz_closefile(file);
+ fz_dropstream(file);
return error;
}
+ fz_dropstream(file);
+ file = temp;
}
strip = 0;
@@ -289,7 +292,7 @@ printf("w=%d h=%d n=%d bpc=%d ",
{
len = fz_read(tiff->file, tmp, MIN(bytecount, sizeof tmp));
if (len < 0)
- return fz_ferror(tiff->file);
+ return fz_throw("ioerror: read failed");
bytecount -= len;
if (tiff->fillorder == 2)
@@ -300,23 +303,16 @@ printf("w=%d h=%d n=%d bpc=%d ",
len = fz_write(file, tmp, len);
if (len < 0)
- return fz_ferror(file);
+ return fz_throw("ioerror: write failed");
}
strip ++;
}
- len = fz_flush(file);
- if (len < 0)
- return fz_ferror(file);
-
if (filter)
- {
- fz_popfilter(file);
fz_dropfilter(filter);
- }
- fz_closefile(file);
+ fz_dropstream(file);
if (tiff->photometric == 3 && tiff->colormap)
{
@@ -453,7 +449,7 @@ tiffreadifd(sa_tiff *tiff, unsigned offset)
}
static fz_error *
-tiffreadifh(sa_tiff *tiff, fz_file *file)
+tiffreadifh(sa_tiff *tiff, fz_stream *file)
{
unsigned version;
unsigned offset;
@@ -488,23 +484,24 @@ tiffreadifh(sa_tiff *tiff, fz_file *file)
}
fz_error *
-sa_readtiff(fz_file *file)
+sa_readtiff(fz_stream *file)
{
fz_error *error;
fz_buffer *buf;
- fz_file *newfile;
+ fz_stream *newfile;
sa_tiff tiff;
+ int n;
/* TIFF requires random access. In Metro TIFFs are embedded in ZIP files.
* Compressed streams are not seekable, so we copy the data to an
* in-memory data buffer instead of reading from the original stream.
*/
- error = fz_readfile(&buf, file);
- if (error)
- return error;
+ n = fz_readall(&buf, file);
+ if (n < 0)
+ return fz_throw("ioerror: readall failed");
- error = fz_openbuffer(&newfile, buf, FZ_READ);
+ error = fz_openrbuffer(&newfile, buf);
if (error)
{
fz_dropbuffer(buf);
@@ -517,7 +514,7 @@ sa_readtiff(fz_file *file)
fz_free(tiff.stripoffsets);
fz_free(tiff.stripbytecounts);
- fz_closefile(newfile);
+ fz_dropstream(newfile);
fz_dropbuffer(buf);
return error;
diff --git a/samus/sa_xml.c b/samus/sa_xml.c
index 198ef6b2..a7b2c764 100644
--- a/samus/sa_xml.c
+++ b/samus/sa_xml.c
@@ -156,7 +156,7 @@ static void ontext(void *zp, const char *buf, int len)
}
fz_error *
-sa_openxml(sa_xmlparser **spp, fz_file *file, int ns)
+sa_openxml(sa_xmlparser **spp, fz_stream *file, int ns)
{
fz_error *error = nil;
sa_xmlparser *sp;
@@ -197,7 +197,7 @@ sa_openxml(sa_xmlparser **spp, fz_file *file, int ns)
len = fz_read(file, buf, XMLBUFLEN);
if (len < 0)
{
- error = fz_ferror(file);
+ error = fz_throw("ioerror: read failed");
goto cleanup;
}
@@ -254,8 +254,8 @@ sa_debugxml(sa_xmlitem *item, int level)
{
indent(level);
- if (sa_isxmltext(item))
- printf("%s\n", sa_xmltext(item));
+ if (strlen(item->name) == 0)
+ printf("%s\n", item->atts[1]);
else
{
printf("<%s", item->name);
@@ -317,50 +317,19 @@ sa_xmlup(sa_xmlparser *sp)
sp->downed --;
}
-int
-sa_isxmlerror(sa_xmlitem *item)
-{
- return item && item->name[0] == '!';
-}
-
-int
-sa_isxmltext(sa_xmlitem *item)
-{
- return item && item->name[0] == '\0';
-}
-
-int
-sa_isxmltag(sa_xmlitem *item)
-{
- return item && item->name[0] != '\0' && item->name[0] != '!';
-}
-
char *
sa_xmlname(sa_xmlitem *item)
{
- if (sa_isxmltag(item))
- return item->name;
- return nil;
+ return item->name;
}
char *
sa_xmlatt(sa_xmlitem *item, char *att)
{
int i;
- if (sa_isxmltag(item))
- {
- for (i = 0; item->atts[i]; i += 2)
- if (!strcmp(item->atts[i], att))
- return item->atts[i + 1];
- }
- return nil;
-}
-
-char *
-sa_xmltext(sa_xmlitem *item)
-{
- if (sa_isxmltext(item))
- return item->atts[1];
+ for (i = 0; item->atts[i]; i += 2)
+ if (!strcmp(item->atts[i], att))
+ return item->atts[i + 1];
return nil;
}
diff --git a/samus/sa_zip.c b/samus/sa_zip.c
index a989f16d..eb182c01 100644
--- a/samus/sa_zip.c
+++ b/samus/sa_zip.c
@@ -12,14 +12,31 @@
#include "fitz.h"
#include "samus.h"
-static inline unsigned int read2(fz_file *f)
+typedef struct sa_zipent_s sa_zipent;
+
+struct sa_zipent_s
+{
+ unsigned offset;
+ unsigned csize;
+ unsigned usize;
+ char *name;
+};
+
+struct sa_zip_s
+{
+ fz_stream *file;
+ int len;
+ sa_zipent *table;
+};
+
+static inline unsigned int read2(fz_stream *f)
{
unsigned char a = fz_readbyte(f);
unsigned char b = fz_readbyte(f);
return (b << 8) | a;
}
-static inline unsigned int read4(fz_file *f)
+static inline unsigned int read4(fz_stream *f)
{
unsigned char a = fz_readbyte(f);
unsigned char b = fz_readbyte(f);
@@ -75,7 +92,7 @@ static fz_error *readzipdir(sa_zip *zip, int startoffset)
fz_seek(zip->file, comsize, 1);
}
- return fz_ferror(zip->file);
+ return nil;
}
static fz_error *readzipendofdir(sa_zip *zip, int startoffset)
@@ -115,7 +132,7 @@ static fz_error *findzipendofdir(sa_zip *zip)
filesize = fz_seek(zip->file, 0, 2);
if (filesize == -1)
- return fz_ferror(zip->file);
+ return fz_throw("ioerror: seek failed");
maxback = MIN(filesize, 0xFFFF + sizeof buf);
back = MIN(maxback, sizeof buf);
@@ -125,7 +142,7 @@ static fz_error *findzipendofdir(sa_zip *zip)
fz_seek(zip->file, filesize - back, 0);
n = fz_read(zip->file, buf, sizeof buf);
if (n < 0)
- return fz_ferror(zip->file);
+ return fz_throw("ioerror: read failed");
for (i = n - 4; i > 0; i--)
if (!memcmp(buf + i, "\120\113\5\6", 4))
@@ -155,7 +172,7 @@ sa_openzip(sa_zip **zipp, char *filename)
zip->len = 0;
zip->table = nil;
- error = fz_openfile(&zip->file, filename, FZ_READ);
+ error = fz_openrfile(&zip->file, filename);
if (error)
return error;
@@ -171,7 +188,7 @@ sa_closezip(sa_zip *zip)
int i;
if (zip->file)
- fz_closefile(zip->file);
+ fz_dropstream(zip->file);
for (i = 0; i < zip->len; i++)
if (zip->table[i].name)
@@ -212,7 +229,7 @@ sa_accesszipentry(sa_zip *zip, char *name)
/*
* Seek and push decoding filter to read an individual file in the zip archive.
*/
-static fz_error *reallyopenzipentry(sa_zip *zip, int idx)
+static fz_error *reallyopenzipentry(fz_stream **stmp, sa_zip *zip, int idx)
{
fz_error *error;
fz_filter *filter;
@@ -224,7 +241,7 @@ static fz_error *reallyopenzipentry(sa_zip *zip, int idx)
t = fz_seek(zip->file, zip->table[idx].offset, 0);
if (t < 0)
- return fz_ferror(zip->file);
+ return fz_throw("ioerror: seek failed");
sign = read4(zip->file);
if (sign != 0x04034b50)
@@ -247,7 +264,9 @@ static fz_error *reallyopenzipentry(sa_zip *zip, int idx)
if (general & 0x0001)
return fz_throw("ioerror: encrypted zip entry");
- fz_seek(zip->file, namesize + metasize, 1);
+ t = fz_seek(zip->file, namesize + metasize, 1);
+ if (t < 0)
+ return fz_throw("ioerror: seek failed");
switch (method)
{
@@ -272,7 +291,7 @@ static fz_error *reallyopenzipentry(sa_zip *zip, int idx)
break;
}
- error = fz_pushfilter(zip->file, filter);
+ error = fz_openrfilter(stmp, filter, zip->file);
fz_dropfilter(filter);
if (error)
return error;
@@ -281,23 +300,14 @@ static fz_error *reallyopenzipentry(sa_zip *zip, int idx)
}
fz_error *
-sa_openzipentry(sa_zip *zip, char *name)
+sa_openzipentry(fz_stream **stmp, sa_zip *zip, char *name)
{
int i;
for (i = 0; i < zip->len; i++)
if (!strcmp(name, zip->table[i].name))
- return reallyopenzipentry(zip, i);
+ return reallyopenzipentry(stmp, zip, i);
return fz_throw("ioerror: file not found in zip: '%s'", name);
}
-/*
- * Pop decompression filter and clean up after reading a file in the archive.
- */
-void
-sa_closezipentry(sa_zip *zip)
-{
- fz_popfilter(zip->file);
-}
-
diff --git a/stream/filt_predict.c b/stream/filt_predict.c
index d7b594ac..f3c50f6e 100644
--- a/stream/filt_predict.c
+++ b/stream/filt_predict.c
@@ -2,7 +2,7 @@
/* TODO: check if this works with 16bpp images */
-enum { MAXC = 16 };
+enum { MAXC = 32 };
typedef struct fz_predict_s fz_predict;
diff --git a/stream/stm_buffer.c b/stream/stm_buffer.c
index 206137a6..7d58e192 100644
--- a/stream/stm_buffer.c
+++ b/stream/stm_buffer.c
@@ -22,7 +22,7 @@ fz_newbuffer(fz_buffer **bp, int size)
}
fz_error *
-fz_newbufferwithdata(fz_buffer **bp, unsigned char *data, int size)
+fz_newbufferwithmemory(fz_buffer **bp, unsigned char *data, int size)
{
fz_buffer *b;
diff --git a/stream/stm_filec.c b/stream/stm_filec.c
deleted file mode 100644
index 93f9ce5a..00000000
--- a/stream/stm_filec.c
+++ /dev/null
@@ -1,349 +0,0 @@
-#include <fitz.h>
-
-fz_error *
-fz_ferror(fz_file *f)
-{
- fz_error *e = f->error;
- f->error = nil;
- return e;
-}
-
-fz_error *
-fz_openfile(fz_file **filep, char *path, int mode)
-{
- fz_error *error;
- fz_file *file;
- int realmode;
- int fd;
- int n;
-
- assert(mode == FZ_READ || mode == FZ_WRITE || mode == FZ_APPEND);
-
- realmode = 0;
- if (mode == FZ_READ)
- realmode = O_BINARY | O_RDONLY;
- if (mode == FZ_WRITE)
- realmode = O_BINARY | O_WRONLY | O_CREAT | O_TRUNC;
- if (mode == FZ_APPEND)
- realmode = O_BINARY | O_WRONLY;
-
- fd = open(path, realmode, 0644);
- if (fd == -1)
- return fz_throw("ioerror: open '%s': %s", path, strerror(errno));
-
- if (mode == FZ_APPEND)
- {
- mode = FZ_WRITE;
- n = lseek(fd, 0, 2);
- if (n == -1) {
- error = fz_throw("ioerror: lseek: %s", strerror(errno));
- close(fd);
- return error;
- }
- }
-
- file = *filep = fz_malloc(sizeof(fz_file));
- if (!file)
- return fz_outofmem;
-
- file->mode = mode;
- file->fd = fd;
- file->depth = 0;
- file->error = nil;
- file->filter = nil;
- file->in = nil;
- file->out = nil;
-
- error = fz_newbuffer(&file->in, FZ_BUFSIZE);
- if (error)
- goto cleanup;
-
- error = fz_newbuffer(&file->out, FZ_BUFSIZE);
- if (error)
- goto cleanup;
-
- return nil;
-
-cleanup:
- *filep = nil;
- close(fd);
- fz_dropbuffer(file->out);
- fz_dropbuffer(file->in);
- fz_free(file);
- return error;
-}
-
-fz_error *
-fz_openbuffer(fz_file **filep, fz_buffer *buf, int mode)
-{
- fz_error *error;
- fz_file *file;
-
- assert(mode == FZ_READ || mode == FZ_WRITE);
-
- file = *filep = fz_malloc(sizeof(fz_file));
- if (!file)
- return fz_outofmem;
-
- file->mode = mode;
- file->fd = -1;
- file->depth = 0;
- file->error = nil;
- file->filter = nil;
-
- if (mode == FZ_READ)
- {
- file->out = fz_keepbuffer(buf);
- error = fz_newbuffer(&file->in, FZ_BUFSIZE);
- if (error)
- goto cleanup;
- }
-
- else
- {
- error = fz_newbuffer(&file->out, FZ_BUFSIZE);
- if (error)
- goto cleanup;
- file->in = fz_keepbuffer(buf);
- }
-
- return nil;
-
-cleanup:
- *filep = nil;
- fz_free(file);
- return error;
-}
-
-void
-fz_closefile(fz_file *file)
-{
- assert(file->depth == 0);
-
- if (file->mode == FZ_WRITE)
- fz_flush(file);
-
- if (file->error)
- {
- fz_warn("%s", file->error->msg);
- fz_droperror(file->error);
- file->error = nil;
- }
-
- if (file->fd != -1) /* open to real file */
- close(file->fd);
-
- fz_dropbuffer(file->in);
- fz_dropbuffer(file->out);
-
- if (file->filter)
- fz_dropfilter(file->filter);
-
- fz_free(file);
-}
-
-fz_error *
-fz_pushfilter(fz_file *file, fz_filter *filter)
-{
- fz_error *error;
-
- /* without a filter, one buffer is ignored: unignore. */
- if (file->depth == 0)
- {
- fz_buffer *buf;
-
- buf = file->out;
- file->out = file->in;
- file->in = buf;
-
- if (file->mode == FZ_READ)
- {
- file->out->rp = file->out->bp;
- file->out->wp = file->out->bp;
- file->out->eof = 0;
- }
- else
- {
- file->out->eof = 0;
- file->in->rp = file->in->bp;
- file->in->wp = file->in->bp;
- file->in->eof = 0;
- }
-
- file->filter = fz_keepfilter(filter);
- }
-
- else
- {
- if (file->mode == FZ_READ)
- {
- error = fz_chainpipeline(&file->filter, file->filter, filter, file->out);
- if (error)
- return error;
-
- error = fz_newbuffer(&file->out, FZ_BUFSIZE);
- if (error)
- {
- fz_unchainpipeline(file->filter, &file->filter, &file->out);
- return error;
- }
- }
-
- else
- {
- error = fz_chainpipeline(&file->filter, filter, file->filter, file->in);
- if (error)
- return error;
-
- error = fz_newbuffer(&file->in, FZ_BUFSIZE);
- if (error)
- {
- fz_unchainpipeline(file->filter, &file->filter, &file->in);
- return error;
- }
- }
- }
-
- file->depth ++;
-
- return nil;
-}
-
-void
-fz_popfilter(fz_file *file)
-{
- fz_buffer *buf;
-
- assert(file->depth > 0);
-
- if (file->mode == FZ_WRITE)
- fz_flush(file);
-
- if (file->error)
- {
- fz_warn("%s", file->error->msg);
- fz_droperror(file->error);
- file->error = nil;
- }
-
- if (file->depth == 1)
- {
- fz_dropfilter(file->filter);
- file->filter = nil;
-
- buf = file->out;
- file->out = file->in;
- file->in = buf;
- }
- else
- {
- if (file->mode == FZ_READ)
- {
- fz_dropbuffer(file->out);
- fz_unchainpipeline(file->filter, &file->filter, &file->out);
- }
- else
- {
- fz_dropbuffer(file->in);
- fz_unchainpipeline(file->filter, &file->filter, &file->in);
- }
- }
-
- file->depth --;
-}
-
-int
-fz_seek(fz_file *f, int ofs, int whence)
-{
- int t;
- int c;
-
- if (f->filter)
- {
- assert(f->mode == FZ_READ && whence == 0);
-
- if (ofs < fz_tell(f))
- {
- f->error = fz_throw("ioerror: cannot seek backwards in filter");
- return -1;
- }
- while (fz_tell(f) < ofs)
- {
- c = fz_readbyte(f);
- if (c == EOF)
- return -1;
- }
- return ofs;
- }
-
- if (whence == 1)
- {
- ofs = fz_tell(f) + ofs;
- whence = 0;
- }
-
- if (f->fd == -1)
- {
- if (whence == 0)
- {
- if (f->mode == FZ_READ)
- f->out->rp = CLAMP(f->out->bp + ofs, f->out->bp, f->out->ep);
- else
- f->in->wp = CLAMP(f->in->bp + ofs, f->in->bp, f->in->ep);
- }
- else
- {
- if (f->mode == FZ_READ)
- f->out->rp = CLAMP(f->out->ep + ofs, f->out->bp, f->out->ep);
- else
- f->in->wp = CLAMP(f->in->ep + ofs, f->in->bp, f->in->ep);
- }
- return fz_tell(f);
- }
-
- t = lseek(f->fd, ofs, whence);
- if (t == -1)
- {
- f->error = fz_throw("ioerror: lseek: %s", strerror(errno));
- return -1;
- }
-
- f->out->rp = f->out->bp;
- f->out->wp = f->out->bp;
- f->out->eof = 0;
-
- return t;
-}
-
-int
-fz_tell(fz_file *f)
-{
- int t;
-
- if (f->filter)
- {
- assert(f->mode == FZ_READ);
- return f->filter->count - (f->out->wp - f->out->rp);
- }
-
- if (f->fd == -1)
- {
- if (f->mode == FZ_READ)
- return f->out->rp - f->out->bp;
- else
- return f->in->wp - f->in->bp;
- }
-
- t = lseek(f->fd, 0, 1);
- if (t == -1)
- {
- f->error = fz_throw("ioerror: lseek: %s", strerror(errno));
- return -1;
- }
-
- if (f->mode == FZ_READ)
- return t - (f->out->wp - f->out->rp);
- else
- return t + (f->in->wp - f->in->rp);
-}
-
diff --git a/stream/stm_filer.c b/stream/stm_filer.c
deleted file mode 100644
index a63a7dd2..00000000
--- a/stream/stm_filer.c
+++ /dev/null
@@ -1,252 +0,0 @@
-#include <fitz.h>
-
-static int doread(fz_buffer *b, int fd)
-{
- int n = read(fd, b->wp, b->ep - b->wp);
- if (n == -1)
- return -1;
- if (n == 0)
- b->eof = 1;
- b->wp += n;
- return n;
-}
-
-int fz_producedata(fz_file *f)
-{
- fz_error *reason;
- int produced;
- int n;
-
- assert(f->mode == FZ_READ);
- assert(f->error == nil);
-
- if (!f->filter)
- {
- fz_rewindbuffer(f->out);
- n = doread(f->out, f->fd);
- if (n < 0) {
- f->error = fz_throw("ioerror in read: %s", strerror(errno));
- return -1;
- }
- return 0;
- }
-
- produced = 0;
-
- while (1)
- {
- reason = fz_process(f->filter, f->in, f->out);
-
- if (f->filter->produced)
- produced = 1;
-
- if (reason == fz_ioneedin)
- {
- if (f->in->eof) {
- f->error = fz_throw("ioerror: premature eof in filter");
- return -1;
- }
-
- /* no space to produce, rewind or grow */
- if (f->in->wp == f->in->ep)
- {
- if (f->in->rp > f->in->bp)
- f->error = fz_rewindbuffer(f->in);
- else
- f->error = fz_growbuffer(f->in);
- if (f->error)
- return -1;
- }
-
- /* then fill with more input */
- n = doread(f->in, f->fd);
- if (n < 0) {
- f->error = fz_throw("ioerror in read: %s", strerror(errno));
- return -1;
- }
-
- if (produced)
- return 0;
- }
-
- else if (reason == fz_ioneedout)
- {
- if (produced)
- return 0;
-
- /* need more outspace, and produced no data */
- if (f->out->rp > f->out->bp)
- f->error = fz_rewindbuffer(f->out);
- else
- f->error = fz_growbuffer(f->out);
- if (f->error)
- return -1;
- }
-
- else if (reason == fz_iodone)
- return 0;
-
- else {
- f->error = reason;
- return -1;
- }
- }
-}
-
-int
-fz_peekbyte(fz_file *f)
-{
- if (f->out->rp == f->out->wp)
- {
- if (f->out->eof) return EOF;
- if (fz_producedata(f)) return EOF;
- }
-
- if (f->out->rp < f->out->wp)
- return *f->out->rp;
-
- return EOF;
-}
-
-int
-fz_readbyte(fz_file *f)
-{
- if (f->out->rp == f->out->wp)
- {
- if (f->out->eof) return EOF;
- if (fz_producedata(f)) return EOF;
- }
-
- if (f->out->rp < f->out->wp)
- return *f->out->rp++;
-
- return EOF;
-}
-
-int
-fz_read(fz_file *f, unsigned char *buf, int n)
-{
- int i = 0;
-
- while (i < n)
- {
- while (f->out->rp < f->out->wp && i < n)
- buf[i++] = *f->out->rp ++;
-
- if (f->out->rp == f->out->wp)
- {
- if (f->out->eof) return i;
- if (fz_producedata(f) < 0) return -1;
- }
- }
-
- return i;
-}
-
-int
-fz_readline(fz_file *f, char *buf, int n)
-{
- int c = EOF;
- char *s = buf;
-
- while (n > 1)
- {
- c = fz_readbyte(f);
- if (c == EOF)
- break;
- if (c == '\r') {
- c = fz_peekbyte(f);
- if (c == '\n')
- c = fz_readbyte(f);
- break;
- }
- if (c == '\n')
- break;
- *s++ = c;
- n--;
- }
- if (n)
- *s = '\0';
- return s - buf;
-}
-
-/*
- * Utility function to consume contents of file stream into
- * a freshly allocated buffer; realloced and trimmed to size.
- */
-
-enum { CHUNKSIZE = 1024 * 32 };
-
-fz_error *
-fz_readfile(fz_buffer **bufp, fz_file *file)
-{
- fz_buffer *real;
- unsigned char *newbuf;
- unsigned char *buf;
- int len;
- int pos;
- int n;
-
- *bufp = nil;
-
- len = 0;
- pos = 0;
- buf = nil;
-
- while (1)
- {
- if (len - pos == 0)
- {
- len += CHUNKSIZE;
- newbuf = fz_realloc(buf, len);
- if (!newbuf)
- {
- fz_free(buf);
- return fz_outofmem;
- }
- buf = newbuf;
- }
-
- n = fz_read(file, buf + pos, len - pos);
-
- if (n < 0)
- {
- fz_free(buf);
- return fz_ferror(file);
- }
-
- pos += n;
-
- if (n < CHUNKSIZE)
- {
- if (pos > 0)
- {
- newbuf = fz_realloc(buf, pos);
- if (!newbuf)
- {
- fz_free(buf);
- return fz_outofmem;
- }
- }
- else newbuf = buf;
-
- real = *bufp = fz_malloc(sizeof(fz_buffer));
- if (!real)
- {
- fz_free(newbuf);
- return fz_outofmem;
- }
-
- real->refs = 1;
- real->ownsdata = 1;
- real->bp = buf;
- real->rp = buf;
- real->wp = buf + pos;
- real->ep = buf + pos;
- real->eof = 1;
-
- return nil;
- }
- }
-}
-
diff --git a/stream/stm_filew.c b/stream/stm_filew.c
deleted file mode 100644
index f83399a2..00000000
--- a/stream/stm_filew.c
+++ /dev/null
@@ -1,260 +0,0 @@
-#include <fitz.h>
-
-int
-fz_printstring(fz_file *f, char *s)
-{
- return fz_write(f, s, strlen(s));
-}
-
-int
-fz_printobj(fz_file *file, fz_obj *obj, int tight)
-{
- char buf[1024];
- char *ptr;
- int n;
-
- n = fz_sprintobj(nil, 0, obj, tight);
- if (n < sizeof buf)
- {
- fz_sprintobj(buf, sizeof buf, obj, tight);
- return fz_write(file, buf, n);
- }
- else
- {
- ptr = fz_malloc(n);
- if (!ptr) {
- file->error = fz_outofmem;
- return -1;
- }
- fz_sprintobj(ptr, n, obj, tight);
- n = fz_write(file, ptr, n);
- fz_free(ptr);
- return n;
- }
-}
-
-int
-fz_print(fz_file *f, char *fmt, ...)
-{
- va_list ap;
- char buf[1024];
- char *p;
- int n;
-
- va_start(ap, fmt);
- n = vsnprintf(buf, sizeof buf, fmt, ap);
- va_end(ap);
-
- if (n < sizeof buf)
- return fz_write(f, buf, n);
-
- p = fz_malloc(n);
- if (!p) {
- f->error = fz_outofmem;
- return -1;
- }
-
- va_start(ap, fmt);
- vsnprintf(p, n, fmt, ap);
- va_end(ap);
-
- n = fz_write(f, p, n);
-
- fz_free(p);
-
- return n;
-}
-
-static int dowrite(fz_buffer *b, int fd)
-{
- int n = write(fd, b->rp, b->wp - b->rp);
- if (n == -1)
- return -1;
- b->rp += n;
- return n;
-}
-
-int
-fz_write(fz_file *f, unsigned char *buf, int n)
-{
- fz_error *reason;
- int i = 0;
- int x;
-
- assert(f->mode == FZ_WRITE);
- assert(f->error == nil);
-
- if (!f->filter)
- {
- while (i < n)
- {
- while (f->in->wp < f->in->ep && i < n)
- *f->in->wp++ = buf[i++];
-
- if (f->in->wp == f->in->ep)
- {
- if (f->fd != -1)
- {
- x = dowrite(f->in, f->fd);
- if (x < 0) {
- f->error = fz_throw("ioerror in write: %s", strerror(errno));
- return -1;
- }
- }
-
- if (f->in->rp > f->in->bp)
- f->error = fz_rewindbuffer(f->in);
- else
- f->error = fz_growbuffer(f->in);
- if (f->error)
- return -1;
- }
- }
-
- return 0;
- }
-
- while (i < n)
- {
- while (f->in->wp < f->in->ep && i < n)
- *f->in->wp++ = buf[i++];
-
- if (f->in->wp == f->in->ep)
- {
- reason = fz_process(f->filter, f->in, f->out);
-
- if (reason == fz_ioneedin)
- {
- if (f->in->wp == f->in->ep) {
- if (f->in->rp > f->in->bp)
- f->error = fz_rewindbuffer(f->in);
- else
- f->error = fz_growbuffer(f->in);
- if (f->error)
- return -1;
- }
- }
-
- else if (reason == fz_ioneedout)
- {
- if (f->fd != -1)
- {
- x = dowrite(f->out, f->fd);
- if (x < 0) {
- f->error = fz_throw("ioerror in write: %s", strerror(errno));
- return -1;
- }
- }
-
- if (f->out->rp > f->out->bp)
- f->error = fz_rewindbuffer(f->out);
- else
- f->error = fz_growbuffer(f->out);
- if (f->error)
- return -1;
- }
-
- else if (reason == fz_iodone)
- {
- if (f->fd != -1)
- {
- while (f->out->rp < f->out->wp)
- {
- x = dowrite(f->out, f->fd);
- if (x < 0) {
- f->error = fz_throw("ioerror in write: %s", strerror(errno));
- return -1;
- }
- }
- }
- break;
- }
-
- else {
- f->error = reason;
- return -1;
- }
- }
- }
-
- return i;
-}
-
-int
-fz_flush(fz_file *f)
-{
- fz_error *reason;
- int n;
-
- assert(f->mode == FZ_WRITE);
- assert(f->error == nil);
-
- f->in->eof = 1;
-
- if (!f->filter)
- {
- if (f->fd != -1)
- {
- while (f->in->rp < f->in->wp)
- {
- n = dowrite(f->in, f->fd);
- if (n < 0) {
- f->error = fz_throw("ioerror in write: %s", strerror(errno));
- return -1;
- }
- }
- }
- return 0;
- }
-
- while (!f->out->eof)
- {
- reason = fz_process(f->filter, f->in, f->out);
-
- if (reason == fz_ioneedin) {
- f->error = fz_throw("ioerror: premature eof in filter");
- return -1;
- }
-
- else if (reason == fz_ioneedout)
- {
- if (f->fd != -1)
- {
- n = dowrite(f->out, f->fd);
- if (n < 0) {
- f->error = fz_throw("ioerror in write: %s", strerror(errno));
- return -1;
- }
- }
-
- if (f->out->rp > f->out->bp)
- f->error = fz_rewindbuffer(f->out);
- else
- f->error = fz_growbuffer(f->out);
- if (f->error)
- return -1;
- }
-
- else if (reason == fz_iodone)
- {
- if (f->fd != -1)
- {
- n = dowrite(f->out, f->fd);
- if (n < 0) {
- f->error = fz_throw("ioerror in write: %s", strerror(errno));
- return -1;
- }
- }
- break;
- }
-
- else
- {
- f->error = reason;
- return -1;
- }
- }
-
- return 0;
-}
-