shithub: pdffs

ref: a9516693e7142a658f4e3ea190272f4cd73b24be
dir: /filter.c/

View raw version
#include <u.h>
#include <libc.h>
#include <bio.h>
#include "pdf.h"

/* 7.4 Filters */

struct Filter {
	char *name;
	int (*readall)(void *aux, Buffer *bi, Buffer *bo);
	int (*open)(Filter *f, Object *o);
	void (*close)(Filter *f);
	void *aux;
};

int fFlate(void *aux, Buffer *bi, Buffer *bo);

static Filter filters[] = {
	{"ASCII85Decode", nil, nil, nil},
	{"ASCIIHexDecode", nil, nil, nil},
	{"CCITTFaxDecode", nil, nil, nil},
	{"CryptDecode", nil, nil, nil},
	{"DCTDecode", nil, nil, nil},
	{"FlateDecode", fFlate},
	{"JBIG2Decode", nil, nil, nil},
	{"JPXDecode", nil, nil, nil},
	{"LZWDecode", nil, nil, nil},
	{"RunLengthDecode", nil, nil, nil},
};

Filter *
filteropen(char *name, Object *o)
{
	int i;
	Filter *f;

	for(i = 0; i < nelem(filters) && strcmp(filters[i].name, name) != 0; i++);
	if(i >= nelem(filters)){
		werrstr("no such filter %q", name);
		return nil;
	}
	if(filters[i].readall == nil){
		werrstr("filter %q not implemented", name);
		return nil;
	}
	if((f = malloc(sizeof(*f))) == nil)
		return nil;
	memmove(f, &filters[i], sizeof(*f));
	if(f->open != nil && f->open(f, o) != 0){
		free(f);
		return nil;
	}

	return f;
}

int
filterrun(Filter *f, Buffer *bi, Buffer *bo)
{
	if(f->readall(f->aux, bi, bo) != 0){
		werrstr("filter[%s]: %r", f->name);
		return -1;
	}
	fprint(2, "filter[%s]: %d → %d %d\n", f->name, bi->sz, bo->sz, bo->off);
	return 0;
}

void
filterclose(Filter *f)
{
	if(f->close != nil)
		f->close(f);
	free(f);
}