#include <X11/Xos.h>
#include <X11/Xfuncs.h>
#include <X11/Xlib.h>
#include <X11/Xutil.h>
#include <stdio.h>
#ifndef WIN32
#include <pwd.h>
#endif
#include "lncmd.h"
#include "xpr.h"
#include <X11/XWDFile.h>
#include <X11/Xmu/SysUtil.h>
#ifndef O_BINARY
#define O_BINARY 0
#endif
#ifdef NLS16
#ifndef NLS
#define NLS
#endif
#endif
#ifndef NLS
#define catgets(i, sn,mn,s) (s)
#else
#define NL_SETN 1
#include <nl_types.h>
nl_catd nlmsg_fd;
#endif
int debug = 0;
#define W_MAX 2400
#define H_MAX 3150
#define W_MARGIN 75
#define H_MARGIN 37
#define W_PAGE 2550
#define H_PAGE 3225
#ifdef NOINLINE
#define min(x,y) (((x)<(y))?(x):(y))
#endif
#define F_PORTRAIT 1
#define F_LANDSCAPE 2
#define F_DUMP 4
#define F_NOSIXOPT 8
#define F_APPEND 16
#define F_NOFF 32
#define F_REPORT 64
#define F_COMPACT 128
#define F_INVERT 256
#define F_GRAY 512
#define F_NPOSITION 1024
#define F_SLIDE 2048
#define DEFAULT_CUTOFF ((unsigned int) (0xFFFF * 0.50))
char *infilename = NULL;
char *progname = NULL;
typedef struct _grayRec {
int level;
int sizeX, sizeY;
unsigned long *grayscales;
} GrayRec, *GrayPtr;
unsigned long grayscale2x2[] =
{0, 1, 9, 11, 15};
unsigned long grayscale3x3[] =
{0, 16, 68, 81, 325, 341, 349, 381, 383, 511};
unsigned long grayscale4x4[] =
{0, 64, 4160, 4161, 20545, 21057, 23105,
23113, 23145, 24169, 24171, 56939, 55275, 55279,
57327, 65519, 65535};
GrayRec gray2x2 = {sizeof(grayscale2x2)/sizeof(long), 2, 2, grayscale2x2};
GrayRec gray3x3 = {sizeof(grayscale3x3)/sizeof(long), 3, 3, grayscale3x3};
GrayRec gray4x4 = {sizeof(grayscale4x4)/sizeof(long), 4, 4, grayscale4x4};
const
char hex1[]="084c2a6e195d3b7f084c2a6e195d3b7f084c2a6e195d3b7f084c2a6e195d3b7f\
084c2a6e195d3b7f084c2a6e195d3b7f084c2a6e195d3b7f084c2a6e195d3b7f\
084c2a6e195d3b7f084c2a6e195d3b7f084c2a6e195d3b7f084c2a6e195d3b7f\
084c2a6e195d3b7f084c2a6e195d3b7f084c2a6e195d3b7f084c2a6e195d3b7f";
const
char hex2[]="000000000000000088888888888888884444444444444444cccccccccccccccc\
2222222222222222aaaaaaaaaaaaaaaa6666666666666666eeeeeeeeeeeeeeee\
111111111111111199999999999999995555555555555555dddddddddddddddd\
3333333333333333bbbbbbbbbbbbbbbb7777777777777777ffffffffffffffff";
static void usage(void);
static
void parse_args(
int argc,
char **argv,
int *scale,
int *width,
int *height,
int *left,
int *top,
enum device *device,
int *flags,
int *split,
char **header,
char **trailer,
int *plane,
GrayPtr *gray,
int *density,
unsigned int *cutoff,
float *gamma,
int *render);
static
void setup_layout(
enum device device,
int win_width,
int win_height,
int flags,
int width,
int height,
char *header,
char *trailer,
int *scale,
enum orientation *orientation);
static
char *convert_data(
XWDFileHeader *win,
char *data,
int plane,
GrayPtr gray,
XColor *colors,
int flags);
static
void dump_sixmap(
register unsigned char (*sixmap)[],
int iw,
int ih);
static
void build_sixmap(
int ih,
int iw,
unsigned char (*sixmap)[],
int hpad,
XWDFileHeader *win,
const char *data);
static void build_output_filename(const char *name, enum device device, char *oname);
static
void ln03_setup(
int iw,
int ih,
enum orientation orientation,
int scale,
int left,
int top,
int *left_margin,
int *top_margin,
int flags,
const char *header,
const char *trailer);
static void ln03_finish(void);
static void la100_setup(int iw, int ih, int scale);
static void la100_finish(void);
static void dump_prolog(int flags);
static int points(int n);
static char *escape(const char *s);
static
void ps_setup(
int iw,
int ih,
enum orientation orientation,
int scale,
int left,
int top,
int flags,
const char *header,
const char *trailer,
const char *name);
static void ps_finish(void);
static void ln03_alter_background(
unsigned char (*sixmap)[],
int iw,
int ih);
static
void ln03_output_sixels(
unsigned char (*sixmap)[],
int iw,
int ih,
int nosixopt,
int split,
int scale,
int top_margin,
int left_margin);
static void la100_output_sixels(
unsigned char (*sixmap)[],
int iw,
int ih,
int nosixopt);
static void ps_output_bits(
int iw,
int ih,
int flags,
enum orientation orientation,
XWDFileHeader *win,
const char *data);
static int ps_putbuf(
register unsigned char *s,
register int n,
register int ocount,
int compact);
static void ps_bitrot(
unsigned char *s,
register int n,
int col,
register int owidth,
char *obuf);
static void fullread (
int file,
char *data,
int nbytes);
int main(int argc, char **argv)
{
unsigned long swaptest = 1;
XWDFileHeader win;
register unsigned char (*sixmap)[];
register int i;
register int iw;
register int ih;
register int sixel_count;
char *w_name;
int scale, width, height, flags, split;
int left, top;
int top_margin, left_margin;
int hpad;
char *header, *trailer;
int plane;
int density, render;
unsigned int cutoff;
float gamma;
GrayPtr gray;
char *data;
long size;
enum orientation orientation;
enum device device;
XColor *colors = (XColor *)NULL;
if (!(progname = argv[0]))
progname = "xpr";
#ifdef NLS
nlmsg_fd = catopen("xpr", 0);
#endif
parse_args (argc, argv, &scale, &width, &height, &left, &top, &device,
&flags, &split, &header, &trailer, &plane, &gray,
&density, &cutoff, &gamma, &render);
if (device == PP) {
x2pmp(stdin, stdout, scale,
width >= 0? inch2pel((float)width/300.0): X_MAX_PELS,
height >= 0? inch2pel((float)height/300.0): Y_MAX_PELS,
left >= 0? inch2pel((float)left/300.0): inch2pel(0.60),
top >= 0? inch2pel((float)top/300.0): inch2pel(0.70),
header, trailer,
(flags & F_PORTRAIT)? PORTRAIT:
((flags & F_LANDSCAPE)? LANDSCAPE: UNSPECIFIED),
(flags & F_INVERT));
exit(0);
} else if ((device == LJET) || (device == PJET) || (device == PJETXL)) {
x2jet(stdin, stdout, scale, density, width, height, left, top,
header, trailer,
(flags & F_PORTRAIT)? PORTRAIT:
((flags & F_LANDSCAPE)? LANDSCAPE: UNSPECIFIED),
(flags & F_INVERT),
((flags & F_APPEND) && !(flags & F_NOFF)),
!(flags & F_NPOSITION),
(flags & F_SLIDE),
device, cutoff, gamma, render);
exit(0);
}
fullread(0, (char *)&win, sizeof win);
if (*(char *) &swaptest)
_swaplong((char *) &win, (long)sizeof(win));
if (win.file_version != XWD_FILE_VERSION) {
fprintf(stderr,"xpr: file format version missmatch.\n");
exit(1);
}
if (win.header_size < sizeof(win)) {
fprintf(stderr,"xpr: header size is too small.\n");
exit(1);
}
w_name = malloc((unsigned)(win.header_size - sizeof win));
fullread(0, w_name, (int) (win.header_size - sizeof win));
if(win.ncolors) {
XWDColor xwdcolor;
colors = (XColor *)malloc((unsigned) (win.ncolors * sizeof(XColor)));
for (i = 0; i < win.ncolors; i++) {
fullread(0, (char*)&xwdcolor, (int) sizeof xwdcolor);
colors[i].pixel = xwdcolor.pixel;
colors[i].red = xwdcolor.red;
colors[i].green = xwdcolor.green;
colors[i].blue = xwdcolor.blue;
colors[i].flags = xwdcolor.flags;
}
if (*(char *) &swaptest) {
for (i = 0; i < win.ncolors; i++) {
_swaplong((char *) &colors[i].pixel, (long)sizeof(long));
_swapshort((char *) &colors[i].red, (long) (3 * sizeof(short)));
}
}
if ((win.ncolors == 2) &&
(INTENSITY(&colors[0]) > INTENSITY(&colors[1])))
flags ^= F_INVERT;
}
if (plane >= (long)win.pixmap_depth) {
fprintf(stderr,"xpr: plane number exceeds image depth\n");
exit(1);
}
size = win.bytes_per_line * win.pixmap_height;
if (win.pixmap_format == XYPixmap)
size *= win.pixmap_depth;
data = malloc((unsigned)size);
fullread(0, data, (int)size);
if ((win.pixmap_depth > 1) || (win.byte_order != win.bitmap_bit_order)) {
data = convert_data(&win, data, plane, gray, colors, flags);
size = win.bytes_per_line * win.pixmap_height;
}
if (win.bitmap_bit_order == MSBFirst) {
_swapbits((unsigned char *)data, size);
win.bitmap_bit_order = LSBFirst;
}
if (flags & F_INVERT)
_invbits((unsigned char *)data, size);
setup_layout(device, (int) win.pixmap_width, (int) win.pixmap_height,
flags, width, height, header, trailer, &scale, &orientation);
if (device == PS) {
iw = win.pixmap_width;
ih = win.pixmap_height;
} else {
iw = win.pixmap_width;
ih = (win.pixmap_height + 5) / 6;
hpad = (ih * 6) - win.pixmap_height;
sixel_count = iw * ih;
sixmap = (unsigned char (*)[])malloc((unsigned)sixel_count);
build_sixmap(iw, ih, sixmap, hpad, &win, data);
}
if (device == LN03) {
ln03_setup(iw, ih, orientation, scale, left, top,
&left_margin, &top_margin, flags, header, trailer);
ln03_output_sixels(sixmap, iw, ih, (flags & F_NOSIXOPT), split,
scale, top_margin, left_margin);
ln03_finish();
} else if (device == LA100) {
la100_setup(iw, ih, scale);
la100_output_sixels(sixmap, iw, ih, (flags & F_NOSIXOPT));
la100_finish();
} else if (device == PS) {
ps_setup(iw, ih, orientation, scale, left, top,
flags, header, trailer, w_name);
ps_output_bits(iw, ih, flags, orientation, &win, data);
ps_finish();
} else {
fprintf(stderr, "xpr: device not supported\n");
}
if (flags & F_REPORT) {
fprintf(stderr, "Name: %s\n", w_name);
fprintf(stderr, "Width: %d, Height: %d\n", win.pixmap_width,
win.pixmap_height);
fprintf(stderr, "Orientation: %s, Scale: %d\n",
(orientation==PORTRAIT) ? "Portrait" : "Landscape", scale);
}
if (((device == LN03) || (device == LA100)) && (flags & F_DUMP))
dump_sixmap(sixmap, iw, ih);
exit(EXIT_SUCCESS);
}
static
void usage(void)
{
fprintf(stderr, "usage: %s [options] [file]\n", progname);
fprintf(stderr, " -append <file> -noff -output <file>\n");
fprintf(stderr, " -compact\n");
fprintf(stderr, " -device {ln03 | la100 | ps | lw | pp | ljet | pjet | pjetxl}\n");
fprintf(stderr, " -dump\n");
fprintf(stderr, " -gamma <correction>\n");
fprintf(stderr, " -gray {2 | 3 | 4}\n");
fprintf(stderr, " -height <inches> -width <inches>\n");
fprintf(stderr, " -header <string> -trailer <string>\n");
fprintf(stderr, " -landscape -portrait\n");
fprintf(stderr, " -left <inches> -top <inches>\n");
fprintf(stderr, " -noposition\n");
fprintf(stderr, " -nosixopt\n");
fprintf(stderr, " -plane <n>\n");
fprintf(stderr, " -psfig\n");
fprintf(stderr, " -render <type>\n");
fprintf(stderr, " -report\n");
fprintf(stderr, " -rv\n");
fprintf(stderr, " -scale <scale>\n");
fprintf(stderr, " -slide\n");
fprintf(stderr, " -split <n-pages>\n");
exit(EXIT_FAILURE);
}
static
void parse_args(
int argc,
char **argv,
int *scale,
int *width,
int *height,
int *left,
int *top,
enum device *device,
int *flags,
int *split,
char **header,
char **trailer,
int *plane,
GrayPtr *gray,
int *density,
unsigned int *cutoff,
float *gamma,
int *render)
{
register char *output_filename;
register int f;
register int len;
register int pos;
output_filename = NULL;
*device = PS;
*flags = 0;
*scale = 0;
*split = 1;
*width = -1;
*height = -1;
*top = -1;
*left = -1;
*header = NULL;
*trailer = NULL;
*plane = -1;
*gray = (GrayPtr)NULL;
*density = 0;
*cutoff = DEFAULT_CUTOFF;
*gamma = -1.0;
*render = 0;
for (argc--, argv++; argc > 0; argc--, argv++) {
if (argv[0][0] != '-') {
infilename = *argv;
continue;
}
len = strlen(*argv);
switch (argv[0][1]) {
case 'a':
if (!bcmp(*argv, "-append", len)) {
argc--; argv++;
if (argc == 0) usage();
output_filename = *argv;
*flags |= F_APPEND;
} else
usage();
break;
case 'c':
if (len <= 2 )
usage();
if (!bcmp(*argv, "-compact", len)) {
*flags |= F_COMPACT;
} else if (!bcmp(*argv, "-cutoff", len)) {
argc--; argv++;
if (argc == 0) usage();
*cutoff = min((atof(*argv) / 100.0 * 0xFFFF), 0xFFFF);
} else
usage();
break;
case 'd':
if (len <= 2)
usage();
if (!bcmp(*argv, "-dump", len)) {
*flags |= F_DUMP;
} else if (len <= 3) {
usage();
} else if (!bcmp(*argv, "-density", len)) {
argc--; argv++;
if (argc == 0) usage();
*density = atoi(*argv);
} else if (!bcmp(*argv, "-device", len)) {
argc--; argv++;
if (argc == 0) usage();
len = strlen(*argv);
if (len < 2)
usage();
if (!bcmp(*argv, "ln03", len)) {
*device = LN03;
} else if (!bcmp(*argv, "la100", len)) {
*device = LA100;
} else if (!bcmp(*argv, "ps", len)) {
*device = PS;
} else if (!bcmp(*argv, "lw", len)) {
*device = PS;
} else if (!bcmp(*argv, "pp", len)) {
*device = PP;
} else if (!bcmp(*argv, "ljet", len)) {
*device = LJET;
} else if (!bcmp(*argv, "pjet", len)) {
*device = PJET;
} else if (!bcmp(*argv, "pjetxl", len)) {
*device = PJETXL;
} else
usage();
} else
usage();
break;
case 'g':
if (len <= 2)
usage();
if (!bcmp(*argv, "-gamma", len)) {
argc--; argv++;
if (argc == 0) usage();
*gamma = atof(*argv);
} else if (!bcmp(*argv, "-gray", len) ||
!bcmp(*argv, "-grey", len)) {
argc--; argv++;
if (argc == 0) usage();
switch (atoi(*argv)) {
case 2:
*gray = &gray2x2;
break;
case 3:
*gray = &gray3x3;
break;
case 4:
*gray = &gray4x4;
break;
default:
usage();
}
*flags |= F_GRAY;
} else
usage();
break;
case 'h':
if (len <= 3)
usage();
if (!bcmp(*argv, "-height", len)) {
argc--; argv++;
if (argc == 0) usage();
*height = (int)(300.0 * atof(*argv));
} else if (!bcmp(*argv, "-header", len)) {
argc--; argv++;
if (argc == 0) usage();
*header = *argv;
} else
usage();
break;
case 'l':
if (len <= 2)
usage();
if (!bcmp(*argv, "-landscape", len)) {
*flags |= F_LANDSCAPE;
} else if (!bcmp(*argv, "-left", len)) {
argc--; argv++;
if (argc == 0) usage();
*left = (int)(300.0 * atof(*argv));
} else
usage();
break;
case 'n':
if (len <= 3)
usage();
if (!bcmp(*argv, "-nosixopt", len)) {
*flags |= F_NOSIXOPT;
} else if (!bcmp(*argv, "-noff", len)) {
*flags |= F_NOFF;
} else if (!bcmp(*argv, "-noposition", len)) {
*flags |= F_NPOSITION;
} else
usage();
break;
case 'o':
if (!bcmp(*argv, "-output", len)) {
argc--; argv++;
if (argc == 0) usage();
output_filename = *argv;
} else
usage();
break;
case 'p':
if (len <= 2)
usage();
if (!bcmp(*argv, "-portrait", len)) {
*flags |= F_PORTRAIT;
} else if (!bcmp(*argv, "-plane", len)) {
argc--; argv++;
if (argc == 0) usage();
*plane = atoi(*argv);
} else if (!bcmp(*argv, "-psfig", len)) {
*flags |= F_NPOSITION;
} else
usage();
break;
case 'r':
if (len <= 2)
usage();
if (!bcmp(*argv, "-rv", len)) {
*flags |= F_INVERT;
} else if (len <= 3) {
usage();
} else if (!bcmp(*argv, "-render", len)) {
argc--; argv++;
if (argc == 0) usage();
*render = atoi(*argv);
} else if (!bcmp(*argv, "-report", len)) {
*flags |= F_REPORT;
} else
usage();
break;
case 's':
if (len <= 2)
usage();
if (!bcmp(*argv, "-scale", len)) {
argc--; argv++;
if (argc == 0) usage();
*scale = atoi(*argv);
} else if (!bcmp(*argv, "-slide", len)) {
*flags |= F_SLIDE;
} else if (!bcmp(*argv, "-split", len)) {
argc--; argv++;
if (argc == 0) usage();
*split = atoi(*argv);
} else
usage();
break;
case 't':
if (len <= 2)
usage();
if (!bcmp(*argv, "-top", len)) {
argc--; argv++;
if (argc == 0) usage();
*top = (int)(300.0 * atof(*argv));
} else if (!bcmp(*argv, "-trailer", len)) {
argc--; argv++;
if (argc == 0) usage();
*trailer = *argv;
} else
usage();
break;
case 'w':
if (!bcmp(*argv, "-width", len)) {
argc--; argv++;
if (argc == 0) usage();
*width = (int)(300.0 * atof(*argv));
} else
usage();
break;
default:
usage();
break;
}
}
if (infilename) {
f = open(infilename, O_RDONLY|O_BINARY, 0);
if (f < 0) {
fprintf(stderr, "xpr: error opening \"%s\" for input\n",
infilename);
perror("");
exit(1);
}
dup2(f, 0);
close(f);
} else
infilename = "stdin";
if (output_filename != NULL) {
if (!(*flags & F_APPEND)) {
f = open(output_filename, O_CREAT|O_WRONLY|O_TRUNC, 0664);
} else {
f = open(output_filename, O_WRONLY, 0);
}
if (f < 0) {
fprintf(stderr, "xpr: error opening \"%s\" for output\n",
output_filename);
perror("xpr");
exit(1);
}
if (*flags & F_APPEND) {
pos = lseek(f, 0, 2);
if ((*flags & F_NOFF) &&
!(*device == LJET || *device == PJET || *device == PJETXL))
pos -= 3;
lseek(f, pos, 0);
}
dup2(f, 1);
close(f);
}
}
static
void setup_layout(
enum device device,
int win_width,
int win_height,
int flags,
int width,
int height,
char *header,
char *trailer,
int *scale,
enum orientation *orientation)
{
register int w_scale;
register int h_scale;
register int iscale = *scale;
register int w_max;
register int h_max;
if (header != NULL) win_height += 75;
if (trailer != NULL) win_height += 75;
if (device == LN03 || device == PS) {
if ((win_width < win_height || (flags & F_PORTRAIT)) &&
!(flags & F_LANDSCAPE)) {
*orientation = PORTRAIT;
w_max = (width > 0)? width : W_MAX;
h_max = (height > 0)? height : H_MAX;
w_scale = w_max / win_width;
h_scale = h_max / win_height;
*scale = min(w_scale, h_scale);
} else {
*orientation = LANDSCAPE;
w_max = (width > 0)? width : H_MAX;
h_max = (height > 0)? height : W_MAX;
w_scale = w_max / win_width;
h_scale = h_max / win_height;
*scale = min(w_scale, h_scale);
}
} else {
*orientation = PORTRAIT;
*scale = W_MAX / win_width;
}
if (*scale == 0) *scale = 1;
if (*scale > 6) *scale = 6;
if (iscale > 0 && iscale < *scale) *scale = iscale;
}
static
char *convert_data(
XWDFileHeader *win,
char *data,
int plane,
GrayPtr gray,
XColor *colors,
int flags)
{
XImage in_image_struct, out_image_struct;
register XImage *in_image, *out_image;
register int x, y;
if ((win->pixmap_format == XYPixmap) && (plane >= 0)) {
data += win->bytes_per_line * win->pixmap_height *
(win->pixmap_depth - (plane + 1));
win->pixmap_format = XYBitmap;
win->pixmap_depth = 1;
return data;
}
in_image = &in_image_struct;
in_image->byte_order = win->byte_order;
in_image->bitmap_unit = win->bitmap_unit;
in_image->bitmap_bit_order = win->bitmap_bit_order;
in_image->depth = win->pixmap_depth;
in_image->bits_per_pixel = win->bits_per_pixel;
in_image->format = win->pixmap_format,
in_image->xoffset = win->xoffset,
in_image->data = data;
in_image->width = win->pixmap_width;
in_image->height = win->pixmap_height;
in_image->bitmap_pad = win->bitmap_pad;
in_image->bytes_per_line = win->bytes_per_line;
in_image->red_mask = win->red_mask;
in_image->green_mask = win->green_mask;
in_image->blue_mask = win->blue_mask;
in_image->obdata = NULL;
if (!XInitImage(in_image)) {
fprintf(stderr,"xpr: bad input image header data.\n");
exit(1);
}
if ((flags & F_GRAY) && (in_image->depth > 1) && (plane < 0)) {
win->pixmap_width *= gray->sizeX;
win->pixmap_height *= gray->sizeY;
}
win->xoffset = 0;
win->pixmap_format = XYBitmap;
win->byte_order = LSBFirst;
win->bitmap_unit = 8;
win->bitmap_bit_order = LSBFirst;
win->bitmap_pad = 8;
win->pixmap_depth = 1;
win->bits_per_pixel = 1;
win->bytes_per_line = (win->pixmap_width + 7) >> 3;
out_image = &out_image_struct;
out_image->byte_order = win->byte_order;
out_image->bitmap_unit = win->bitmap_unit;
out_image->bitmap_bit_order = win->bitmap_bit_order;
out_image->depth = win->pixmap_depth;
out_image->bits_per_pixel = win->bits_per_pixel;
out_image->format = win->pixmap_format;
out_image->xoffset = win->xoffset,
out_image->width = win->pixmap_width;
out_image->height = win->pixmap_height;
out_image->bitmap_pad = win->bitmap_pad;
out_image->bytes_per_line = win->bytes_per_line;
out_image->red_mask = 0;
out_image->green_mask = 0;
out_image->blue_mask = 0;
out_image->obdata = NULL;
out_image->data = malloc((unsigned)out_image->bytes_per_line *
out_image->height);
if (!XInitImage(out_image)) {
fprintf(stderr,"xpr: bad output image header data.\n");
exit(1);
}
if ((in_image->depth > 1) && (plane > 0)) {
for (y = 0; y < in_image->height; y++)
for (x = 0; x < in_image->width; x++)
XPutPixel(out_image, x, y,
(XGetPixel(in_image, x, y) >> plane) & 1);
} else if (plane == 0) {
for (y = 0; y < in_image->height; y++)
for (x = 0; x < in_image->width; x++)
XPutPixel(out_image, x, y, XGetPixel(in_image, x, y));
} else if ((in_image->depth > 1) &&
((win->visual_class == TrueColor) ||
(win->visual_class == DirectColor))) {
XColor color;
int direct = 0;
unsigned long rmask, gmask, bmask;
int rshift = 0, gshift = 0, bshift = 0;
rmask = win->red_mask;
while (!(rmask & 1)) {
rmask >>= 1;
rshift++;
}
gmask = win->green_mask;
while (!(gmask & 1)) {
gmask >>= 1;
gshift++;
}
bmask = win->blue_mask;
while (!(bmask & 1)) {
bmask >>= 1;
bshift++;
}
if ((win->ncolors == 0) || (win->visual_class == DirectColor))
direct = 1;
if (flags & F_GRAY) {
register int ox, oy;
int ix, iy;
unsigned long bits;
for (y = 0, oy = 0; y < in_image->height; y++, oy += gray->sizeY)
for (x = 0, ox = 0; x < in_image->width; x++, ox += gray->sizeX)
{
color.pixel = XGetPixel(in_image, x, y);
color.red = (color.pixel >> rshift) & rmask;
color.green = (color.pixel >> gshift) & gmask;
color.blue = (color.pixel >> bshift) & bmask;
if (!direct) {
color.red = colors[color.red].red;
color.green = colors[color.green].green;
color.blue = colors[color.blue].blue;
}
bits = gray->grayscales[(int)(gray->level *
INTENSITY(&color)) /
(INTENSITYPER(100) + 1)];
for (iy = 0; iy < gray->sizeY; iy++)
for (ix = 0; ix < gray->sizeX; ix++, bits >>= 1)
XPutPixel(out_image, ox + ix, oy + iy, bits);
}
} else {
for (y = 0; y < in_image->height; y++)
for (x = 0; x < in_image->width; x++) {
color.pixel = XGetPixel(in_image, x, y);
color.red = (color.pixel >> rshift) & rmask;
color.green = (color.pixel >> gshift) & gmask;
color.blue = (color.pixel >> bshift) & bmask;
if (!direct) {
color.red = colors[color.red].red;
color.green = colors[color.green].green;
color.blue = colors[color.blue].blue;
}
XPutPixel(out_image, x, y,
INTENSITY(&color) > HALFINTENSITY);
}
}
} else if (flags & F_GRAY) {
register int ox, oy;
int ix, iy;
unsigned long bits;
if (win->ncolors == 0) {
fprintf(stderr, "no colors in data, can't remap\n");
exit(1);
}
for (x = 0; x < win->ncolors; x++) {
register XColor *color = &colors[x];
color->pixel = gray->grayscales[(gray->level * INTENSITY(color)) /
(INTENSITYPER(100) + 1)];
}
for (y = 0, oy = 0; y < in_image->height; y++, oy += gray->sizeY)
for (x = 0, ox = 0; x < in_image->width; x++, ox += gray->sizeX) {
bits = colors[XGetPixel(in_image, x, y)].pixel;
for (iy = 0; iy < gray->sizeY; iy++)
for (ix = 0; ix < gray->sizeX; ix++, bits >>= 1)
XPutPixel(out_image, ox + ix, oy + iy, bits);
}
} else {
if (win->ncolors == 0) {
fprintf(stderr, "no colors in data, can't remap\n");
exit(1);
}
for (x = 0; x < win->ncolors; x++) {
register XColor *color = &colors[x];
color->pixel = (INTENSITY(color) > HALFINTENSITY);
}
for (y = 0; y < in_image->height; y++)
for (x = 0; x < in_image->width; x++)
XPutPixel(out_image, x, y,
colors[XGetPixel(in_image, x, y)].pixel);
}
free(data);
return (out_image->data);
}
static
void dump_sixmap(
register unsigned char (*sixmap)[],
int iw,
int ih)
{
register int i, j;
register unsigned char *c;
c = (unsigned char *)sixmap;
fprintf(stderr, "Sixmap:\n");
for (i = 0; i < ih; i++) {
for (j = 0; j < iw; j++) {
fprintf(stderr, "%02X ", *c++);
}
fprintf(stderr, "\n\n");
}
}
static
void build_sixmap(
int ih,
int iw,
unsigned char (*sixmap)[],
int hpad,
XWDFileHeader *win,
const char *data)
{
int iwb = win->bytes_per_line;
unsigned char *line[6];
register unsigned char *c;
register int i, j;
#ifdef NOINLINE
register int w;
#endif
register int sixel;
unsigned char *buffer = (unsigned char *)data;
c = (unsigned char *)sixmap;
while (--ih >= 0) {
for (i = 0; i <= 5; i++) {
line[i] = buffer;
buffer += iwb;
}
if ((ih == 0) && (hpad > 0)) {
unsigned char *ffbuf;
ffbuf = (unsigned char *)malloc((unsigned)iwb);
for (j = 0; j < iwb; j++)
ffbuf[j] = 0xFF;
for (; --hpad >= 0; i--)
line[i] = ffbuf;
}
#ifndef NOINLINE
for (i = 0; i < iw; i++) {
sixel = extzv(line[0], i, 1);
sixel |= extzv(line[1], i, 1) << 1;
sixel |= extzv(line[2], i, 1) << 2;
sixel |= extzv(line[3], i, 1) << 3;
sixel |= extzv(line[4], i, 1) << 4;
sixel |= extzv(line[5], i, 1) << 5;
*c++ = sixel;
}
#else
for (i = 0, w = iw; w > 0; i++) {
for (j = 0; j <= 7; j++) {
sixel = ((line[0][i] >> j) & 1);
sixel |= ((line[1][i] >> j) & 1) << 1;
sixel |= ((line[2][i] >> j) & 1) << 2;
sixel |= ((line[3][i] >> j) & 1) << 3;
sixel |= ((line[4][i] >> j) & 1) << 4;
sixel |= ((line[5][i] >> j) & 1) << 5;
*c++ = sixel;
if (--w == 0) break;
}
}
#endif
}
}
static
void build_output_filename(const char *name, enum device device, char *oname)
{
while (*name && *name != '.') *oname++ = *name++;
switch (device) {
case LN03: bcopy(".ln03", oname, 6); break;
case LA100: bcopy(".la100", oname, 7); break;
}
}
static
void ln03_setup(
int iw,
int ih,
enum orientation orientation,
int scale,
int left,
int top,
int *left_margin,
int *top_margin,
int flags,
const char *header,
const char *trailer)
{
register int i;
register int lm, tm, xm;
char buf[256];
register char *bp = buf;
if (!(flags & F_APPEND)) {
sprintf(bp, LN_STR); bp += 4;
sprintf(bp, LN_SSU, 7); bp += 5;
sprintf(bp, LN_PUM_SET); bp += sizeof LN_PUM_SET - 1;
}
if (orientation == PORTRAIT) {
lm = (left > 0)? left : (((W_MAX - scale * iw) / 2) + W_MARGIN);
tm = (top > 0)? top : (((H_MAX - scale * ih * 6) / 2) + H_MARGIN);
sprintf(bp, LN_PFS, "?20"); bp += 7;
sprintf(bp, LN_DECOPM_SET); bp += sizeof LN_DECOPM_SET - 1;
sprintf(bp, LN_DECSLRM, lm, W_PAGE - lm); bp += strlen(bp);
} else {
lm = (left > 0)? left : (((H_MAX - scale * iw) / 2) + H_MARGIN);
tm = (top > 0)? top : (((W_MAX - scale * ih * 6) / 2) + W_MARGIN);
sprintf(bp, LN_PFS, "?21"); bp += 7;
sprintf(bp, LN_DECOPM_SET); bp += sizeof LN_DECOPM_SET - 1;
sprintf(bp, LN_DECSLRM, lm, H_PAGE - lm); bp += strlen(bp);
}
if (header != NULL) {
sprintf(bp, LN_VPA, tm - 100); bp += strlen(bp);
i = strlen(header);
xm = (((scale * iw) - (i * 30)) / 2) + lm;
sprintf(bp, LN_HPA, xm); bp += strlen(bp);
sprintf(bp, LN_SGR, 3); bp += strlen(bp);
bcopy(header, bp, i);
bp += i;
}
if (trailer != NULL) {
sprintf(bp, LN_VPA, tm + (scale * ih * 6) + 75); bp += strlen(bp);
i = strlen(trailer);
xm = (((scale * iw) - (i * 30)) / 2) + lm;
sprintf(bp, LN_HPA, xm); bp += strlen(bp);
sprintf(bp, LN_SGR, 3); bp += strlen(bp);
bcopy(trailer, bp, i);
bp += i;
}
sprintf(bp, LN_HPA, lm); bp += strlen(bp);
sprintf(bp, LN_VPA, tm); bp += strlen(bp);
sprintf(bp, LN_SIXEL_GRAPHICS, 9, 0, scale); bp += strlen(bp);
sprintf(bp, "\"1;1"); bp += 4;
write(1, buf, bp-buf);
*top_margin = tm;
*left_margin = lm;
}
static
void ln03_finish(void)
{
char buf[256];
register char *bp = buf;
sprintf(bp, LN_DECOPM_RESET); bp += sizeof LN_DECOPM_SET - 1;
sprintf(bp, LN_LNM); bp += 5;
sprintf(bp, LN_PUM); bp += 5;
sprintf(bp, LN_PFS, "?20"); bp += 7;
sprintf(bp, LN_SGR, 0); bp += strlen(bp);
sprintf(bp, LN_HPA, 1); bp += strlen(bp);
sprintf(bp, LN_VPA, 1); bp += strlen(bp);
write(1, buf, bp-buf);
}
static
void la100_setup(int iw, int ih, int scale)
{
char buf[256];
register char *bp;
int lm, tm;
bp = buf;
lm = ((80 - (int)((double)iw / 6.6)) / 2) - 1;
if (lm < 1) lm = 1;
tm = ((66 - (int)((double)ih / 2)) / 2) - 1;
if (tm < 1) tm = 1;
sprintf(bp, "\033[%d;%ds", lm, 81-lm); bp += strlen(bp);
sprintf(bp, "\033[?7l"); bp += 5;
sprintf(bp, "\033[%dd", tm); bp += strlen(bp);
sprintf(bp, "\033[%d`", lm); bp += strlen(bp);
sprintf(bp, "\033P0q"); bp += 4;
write(1, buf, bp-buf);
}
#define LA100_RESET "\033[1;80s\033[?7h"
static
void la100_finish(void)
{
write(1, LA100_RESET, sizeof LA100_RESET - 1);
}
#define COMMENTVERSION "PS-Adobe-1.0"
#ifdef XPROLOG
static
void dump_prolog(int flags)
{
char *fname=(flags & F_COMPACT) ? "prolog.compact" : "prolog";
FILE *fi = fopen(fname,"r");
char buf[1024];
if (fi==NULL) {
perror(fname);
exit(1);
}
while (fgets(buf,1024,fi)) fputs(buf,stdout);
fclose(fi);
}
#else
const
char *ps_prolog_compact[] = {
"%%Pages: 1",
"%%EndProlog",
"%%Page: 1 1",
"",
"/bitgen",
" {",
" /nextpos 0 def",
" currentfile bufspace readhexstring pop % get a chunk of input",
" % interpret each byte of the input",
" {",
" flag { % if the previous byte was FF",
" /len exch def % this byte is a count",
" result",
" nextpos",
" FFstring 0 len getinterval % grap a chunk of FF's",
" putinterval % and stuff them into the result",
" /nextpos nextpos len add def",
" /flag false def",
" }{ % otherwise",
" dup 255 eq { % if this byte is FF",
" /flag true def % just set the flag",
" pop % and toss the FF",
" }{ % otherwise",
" % move this byte to the result",
" result nextpos",
" 3 -1 roll % roll the current byte back to the top",
" put",
" /nextpos nextpos 1 add def",
" } ifelse",
" } ifelse",
" } forall",
" % trim unused space from end of result",
" result 0 nextpos getinterval",
" } def",
"",
"",
"/bitdump % stk: width, height, iscale",
" % dump a bit image with lower left corner at current origin,",
" % scaling by iscale (iscale=1 means 1/300 inch per pixel)",
" {",
" % read arguments",
" /iscale exch def",
" /height exch def",
" /width exch def",
"",
" % scale appropriately",
" width iscale mul height iscale mul scale",
"",
" % data structures:",
"",
" % allocate space for one line of input",
" /bufspace 36 string def",
"",
" % string of FF's",
" /FFstring 256 string def",
" % for all i FFstring[i]=255",
" 0 1 255 { FFstring exch 255 put } for",
"",
" % 'escape' flag",
" /flag false def",
"",
" % space for a chunk of generated bits",
" /result 4590 string def",
"",
" % read and dump the image",
" width height 1 [width 0 0 height neg 0 height]",
" { bitgen }",
" image",
" } def",
0
};
const
char *ps_prolog[] = {
"%%Pages: 1",
"%%EndProlog",
"%%Page: 1 1",
"",
"/bitdump % stk: width, height, iscale",
"% dump a bit image with lower left corner at current origin,",
"% scaling by iscale (iscale=1 means 1/300 inch per pixel)",
"{",
" % read arguments",
" /iscale exch def",
" /height exch def",
" /width exch def",
"",
" % scale appropriately",
" width iscale mul height iscale mul scale",
"",
" % allocate space for one scanline of input",
" /picstr % picstr holds one scan line",
" width 7 add 8 idiv % width of image in bytes = ceiling(width/8)",
" string",
" def",
"",
" % read and dump the image",
" width height 1 [width 0 0 height neg 0 height]",
" { currentfile picstr readhexstring pop }",
" image",
"} def",
0
};
static
void dump_prolog(int flags) {
const char **p = (flags & F_COMPACT) ? ps_prolog_compact : ps_prolog;
while (*p)
printf("%s\n", *p++);
}
#endif
#define PAPER_WIDTH 85*30
#define PAPER_LENGTH 11*300
static
int points(int n)
{
n *= 72;
return n/300;
}
static
char *escape(const char *s)
{
static char buf[200];
char *p = buf;
for (;*s;s++) {
if (*s < ' ' || *s > 0176) continue;
if (*s==')' || *s=='(' || *s == '\\') {
sprintf(p,"\\%03o",*s);
p += 4;
}
else *p++ = *s;
}
*p = 0;
return buf;
}
static
void ps_setup(
int iw,
int ih,
enum orientation orientation,
int scale,
int left,
int top,
int flags,
const char *header,
const char *trailer,
const char *name)
{
char hostname[256];
#ifdef WIN32
char *username;
#else
struct passwd *pswd;
#endif
long clock;
int lm, bm;
if (orientation==PORTRAIT) {
lm = (left > 0)? left : ((PAPER_WIDTH - scale * iw) / 2);
bm = (top > 0)? (PAPER_LENGTH - top - scale * ih)
: ((PAPER_LENGTH - scale * ih) / 2);
} else {
lm = (top > 0)? (PAPER_WIDTH - top - scale * ih)
: ((PAPER_WIDTH - scale * ih) / 2);
bm = (left > 0)? (PAPER_LENGTH - left - scale * iw)
: ((PAPER_LENGTH - scale * iw) / 2);
}
printf ("%%!%s\n", COMMENTVERSION);
printf ("%%%%BoundingBox: %d %d %d %d\n",
(flags & F_NPOSITION) ? points(lm) : 0,
(flags & F_NPOSITION) ? points(bm) : 0,
points(iw * scale), points(ih * scale));
(void) XmuGetHostname (hostname, sizeof hostname);
#ifdef WIN32
username = getenv("USERNAME");
printf ("%%%%Creator: %s:%s\n", hostname,
username ? username : "unknown");
#else
pswd = getpwuid (getuid ());
printf ("%%%%Creator: %s:%s (%s)\n", hostname,
pswd->pw_name, pswd->pw_gecos);
#endif
printf ("%%%%Title: %s (%s)\n", infilename,name);
printf ("%%%%CreationDate: %s",
(time (&clock), ctime (&clock)));
printf ("%%%%EndComments\n");
dump_prolog(flags);
if (orientation==PORTRAIT) {
if (header || trailer) {
printf("gsave\n");
printf("/Times-Roman findfont 15 scalefont setfont\n");
printf("%d %d translate\n",points(lm),points(bm));
if (header) {
char *label = escape(header);
printf("%d (%s) stringwidth pop sub 2 div %d moveto\n",
points(iw*scale), label, points(ih*scale) + 10);
printf("(%s) show\n",label);
}
if (trailer) {
char *label = escape(trailer);
printf("%d (%s) stringwidth pop sub 2 div -20 moveto\n",
points(iw*scale), label);
printf("(%s) show\n",label);
}
printf("grestore\n");
}
printf("72 300 div dup scale\n");
if (!(flags & F_NPOSITION))
printf("%d %d translate\n",lm,bm);
printf("%d %d %d bitdump\n",iw,ih,scale);
} else {
if (header || trailer) {
printf("gsave\n");
printf("/Times-Roman findfont 15 scalefont setfont\n");
printf("%d %d translate\n",points(lm),points(bm + scale * iw));
printf("-90 rotate\n");
if (header) {
char *label = escape(header);
printf("%d (%s) stringwidth pop sub 2 div %d moveto\n",
points(iw*scale), label, points(ih*scale) + 10);
printf("(%s) show\n",label);
}
if (trailer) {
char *label = escape(trailer);
printf("%d (%s) stringwidth pop sub 2 div -20 moveto\n",
points(iw*scale), label);
printf("(%s) show\n",label);
}
printf("grestore\n");
}
printf("72 300 div dup scale\n");
if (!(flags & F_NPOSITION))
printf("%d %d translate\n",lm,bm);
printf("%d %d %d bitdump\n",ih,iw,scale);
}
}
const
char *ps_epilog[] = {
"",
"showpage",
"%%Trailer",
0
};
static
void ps_finish(void)
{
char **p = ps_epilog;
while (*p) printf("%s\n",*p++);
}
static
void ln03_alter_background(
unsigned char (*sixmap)[],
int iw,
int ih)
{
register unsigned char *c, *stopc;
register unsigned char *startc;
register int n;
c = (unsigned char *)sixmap;
stopc = c + (iw * ih);
n = 0;
while (c < stopc) {
switch (*c) {
case 0x08: case 0x11: case 0x04: case 0x22:
case 0x20: case 0x21: case 0x24: case 0x00:
if (n == 0) startc = c;
n++;
break;
default:
if (n >= 2) {
while (n-- > 0) *startc++ = 0x00;
} else {
n = 0;
}
break;
}
c++;
}
}
static
void ln03_output_sixels(
unsigned char (*sixmap)[],
int iw,
int ih,
int nosixopt,
int split,
int scale,
int top_margin,
int left_margin)
{
unsigned char *buf;
register unsigned char *bp;
int i;
int j;
register int k;
register unsigned char *c;
register int lastc;
register int count;
char snum[6];
register char *snp;
bp = (unsigned char *)malloc((unsigned)(iw*ih+512));
buf = bp;
count = 0;
lastc = -1;
c = (unsigned char *)sixmap;
split = ih / split;
iw--;
for (i = 0; i < ih; i++) {
for (j = 0; j <= iw; j++) {
if (!nosixopt) {
if (*c == lastc && j < iw) {
count++;
c++;
continue;
}
if (count >= 3) {
bp--;
count++;
*bp++ = '!';
snp = snum;
while (count > 0) {
k = count / 10;
*snp++ = count - (k * 10) + '0';
count = k;
}
while (--snp >= snum) *bp++ = *snp;
*bp++ = (~lastc & 0x3F) + 0x3F;
} else if (count > 0) {
lastc = (~lastc & 0x3F) + 0x3F;
do {
*bp++ = lastc;
} while (--count > 0);
}
}
lastc = *c++;
*bp++ = (~lastc & 0x3F) + 0x3F;
}
*bp++ = '-';
lastc = -1;
if ((i % split) == 0 && i != 0) {
sprintf((char *)bp, LN_ST); bp += sizeof LN_ST - 1;
*bp++ = '\f';
sprintf((char *)bp, LN_VPA, top_margin + (i * 6 * scale));
bp += strlen((char *)bp);
sprintf((char *)bp, LN_HPA, left_margin);
bp += strlen((char *)bp);
sprintf((char *)bp, LN_SIXEL_GRAPHICS, 9, 0, scale);
bp += strlen((char *)bp);
sprintf((char *)bp, "\"1;1"); bp += 4;
}
}
sprintf((char *)bp, LN_ST); bp += sizeof LN_ST - 1;
write(1, (char *)buf, bp-buf);
}
static
void la100_output_sixels(
unsigned char (*sixmap)[],
int iw,
int ih,
int nosixopt)
{
unsigned char *buf;
register unsigned char *bp;
int i;
register int j, k;
register unsigned char *c;
register int lastc;
register int count;
char snum[6];
bp = (unsigned char *)malloc((unsigned)(iw*ih+512));
buf = bp;
count = 0;
lastc = -1;
c = (unsigned char *)sixmap;
for (i = 0; i < ih; i++) {
for (j = 0; j < iw; j++) {
if (*c == lastc && (j+1) < iw) {
count++;
c++;
continue;
}
if (count >= 2) {
bp -= 2;
count = 2 * (count + 1);
*bp++ = '!';
k = 0;
while (count > 0) {
snum[k++] = (count % 10) + '0';
count /= 10;
}
while (--k >= 0) *bp++ = snum[k];
*bp++ = (~lastc & 0x3F) + 0x3F;
count = 0;
} else if (count > 0) {
lastc = (~lastc & 0x3F) + 0x3F;
do {
*bp++ = lastc;
*bp++ = lastc;
} while (--count > 0);
}
lastc = (~*c & 0x3F) + 0x3F;
*bp++ = lastc;
*bp++ = lastc;
lastc = *c++;
}
*bp++ = '-';
lastc = -1;
}
sprintf((char *)bp, LN_ST); bp += sizeof LN_ST - 1;
*bp++ = '\f';
write(1, (char *)buf, bp-buf);
}
#define LINELEN 72
static
void ps_output_bits(
int iw,
int ih,
int flags,
enum orientation orientation,
XWDFileHeader *win,
const char *data)
{
unsigned long swaptest = 1;
int iwb = win->bytes_per_line;
register int i;
int bytes;
unsigned char *buffer = (unsigned char *)data;
register int ocount=0;
static char hex[] = "0123456789abcdef";
if (orientation == LANDSCAPE) {
int ocol = ih;
int owidth = (ih+31)/32;
int oheight = (iw+31)/32;
register char *p, *q;
char *obuf;
unsigned char *ibuf;
owidth *= 4;
oheight *= 32;
obuf = malloc((unsigned)(owidth*oheight));
if (obuf==0) {
fprintf(stderr,"xpr: cannot allocate %d bytes\n",owidth*oheight);
exit(1);
}
bzero(obuf,owidth*oheight);
ibuf = (unsigned char *)malloc((unsigned)(iwb + 3));
for (i=0;i<ih;i++) {
bcopy((char *)buffer, (char *)ibuf, iwb);
buffer += iwb;
if (!(*(char *) &swaptest))
_swaplong((char *)ibuf,(long)iwb);
ps_bitrot(ibuf,iw,--ocol,owidth,obuf);
}
if (!(*(char *) &swaptest))
_swaplong(obuf,(long)(iw*owidth));
q = &obuf[iw*owidth];
bytes = (ih+7)/8;
for (p=obuf;p<q;p+=owidth)
ocount = ps_putbuf((unsigned char *)p,bytes,ocount,flags&F_COMPACT);
}
else {
for (i=0;i<ih;i++) {
ocount = ps_putbuf(buffer,(iw+7)/8,ocount,flags&F_COMPACT);
buffer += iwb;
}
}
if (flags & F_COMPACT) {
if (ocount) {
while (ocount++ < LINELEN)
putchar(hex[ocount&15]);
putchar('\n');
}
}
}
const
unsigned char _reverse_byte[0x100] = {
0x00, 0x80, 0x40, 0xc0, 0x20, 0xa0, 0x60, 0xe0,
0x10, 0x90, 0x50, 0xd0, 0x30, 0xb0, 0x70, 0xf0,
0x08, 0x88, 0x48, 0xc8, 0x28, 0xa8, 0x68, 0xe8,
0x18, 0x98, 0x58, 0xd8, 0x38, 0xb8, 0x78, 0xf8,
0x04, 0x84, 0x44, 0xc4, 0x24, 0xa4, 0x64, 0xe4,
0x14, 0x94, 0x54, 0xd4, 0x34, 0xb4, 0x74, 0xf4,
0x0c, 0x8c, 0x4c, 0xcc, 0x2c, 0xac, 0x6c, 0xec,
0x1c, 0x9c, 0x5c, 0xdc, 0x3c, 0xbc, 0x7c, 0xfc,
0x02, 0x82, 0x42, 0xc2, 0x22, 0xa2, 0x62, 0xe2,
0x12, 0x92, 0x52, 0xd2, 0x32, 0xb2, 0x72, 0xf2,
0x0a, 0x8a, 0x4a, 0xca, 0x2a, 0xaa, 0x6a, 0xea,
0x1a, 0x9a, 0x5a, 0xda, 0x3a, 0xba, 0x7a, 0xfa,
0x06, 0x86, 0x46, 0xc6, 0x26, 0xa6, 0x66, 0xe6,
0x16, 0x96, 0x56, 0xd6, 0x36, 0xb6, 0x76, 0xf6,
0x0e, 0x8e, 0x4e, 0xce, 0x2e, 0xae, 0x6e, 0xee,
0x1e, 0x9e, 0x5e, 0xde, 0x3e, 0xbe, 0x7e, 0xfe,
0x01, 0x81, 0x41, 0xc1, 0x21, 0xa1, 0x61, 0xe1,
0x11, 0x91, 0x51, 0xd1, 0x31, 0xb1, 0x71, 0xf1,
0x09, 0x89, 0x49, 0xc9, 0x29, 0xa9, 0x69, 0xe9,
0x19, 0x99, 0x59, 0xd9, 0x39, 0xb9, 0x79, 0xf9,
0x05, 0x85, 0x45, 0xc5, 0x25, 0xa5, 0x65, 0xe5,
0x15, 0x95, 0x55, 0xd5, 0x35, 0xb5, 0x75, 0xf5,
0x0d, 0x8d, 0x4d, 0xcd, 0x2d, 0xad, 0x6d, 0xed,
0x1d, 0x9d, 0x5d, 0xdd, 0x3d, 0xbd, 0x7d, 0xfd,
0x03, 0x83, 0x43, 0xc3, 0x23, 0xa3, 0x63, 0xe3,
0x13, 0x93, 0x53, 0xd3, 0x33, 0xb3, 0x73, 0xf3,
0x0b, 0x8b, 0x4b, 0xcb, 0x2b, 0xab, 0x6b, 0xeb,
0x1b, 0x9b, 0x5b, 0xdb, 0x3b, 0xbb, 0x7b, 0xfb,
0x07, 0x87, 0x47, 0xc7, 0x27, 0xa7, 0x67, 0xe7,
0x17, 0x97, 0x57, 0xd7, 0x37, 0xb7, 0x77, 0xf7,
0x0f, 0x8f, 0x4f, 0xcf, 0x2f, 0xaf, 0x6f, 0xef,
0x1f, 0x9f, 0x5f, 0xdf, 0x3f, 0xbf, 0x7f, 0xff
};
void _invbits (
register unsigned char *b,
register long n)
{
do {
*b = ~*b;
b++;
} while (--n > 0);
}
void _swapbits (
register unsigned char *b,
register long n)
{
do {
*b = _reverse_byte[*b];
b++;
} while (--n > 0);
}
void _swapshort (
register char *bp,
register long n)
{
register char c;
register char *ep = bp + n;
do {
c = *bp;
*bp = *(bp + 1);
bp++;
*bp = c;
bp++;
}
while (bp < ep);
}
void _swaplong (
register char *bp,
register long n)
{
register char c;
register char *ep = bp + n;
register char *sp;
do {
sp = bp + 3;
c = *sp;
*sp = *bp;
*bp++ = c;
sp = bp + 1;
c = *sp;
*sp = *bp;
*bp++ = c;
bp += 2;
}
while (bp < ep);
}
static
int ps_putbuf(
register unsigned char *s,
register int n,
register int ocount,
int compact)
{
register int ffcount = 0;
static char hex[] = "0123456789abcdef";
#define PUT(c) { putchar(c); if (++ocount>=LINELEN) \
{ putchar('\n'); ocount=0; }}
if (compact) {
while (n--) {
if (*s == 0xff) {
if (++ffcount == 255) {
PUT('f'); PUT('f');
PUT('f'); PUT('f');
ffcount = 0;
}
}
else {
if (ffcount) {
PUT('f'); PUT('f');
PUT(hex[ffcount >> 4]);
PUT(hex[ffcount & 0xf]);
ffcount = 0;
}
PUT(hex1[*s]);
PUT(hex2[*s]);
}
s++;
}
if (ffcount) {
PUT('f'); PUT('f');
PUT(hex[ffcount >> 4]);
PUT(hex[ffcount & 0xf]);
ffcount = 0;
}
}
else {
while (n--) {
putchar(hex1[*s]);
putchar(hex2[*s++]);
}
putchar('\n');
}
return ocount;
}
static
void ps_bitrot(
unsigned char *s,
register int n,
int col,
register int owidth,
char *obuf)
{
register int mask = 1<<(col%32);
register int iword;
register int b = 0;
register char *opos = obuf + (col/32)*4;
register int *iwordp = (int *) s;
while (--n>=0) {
if (--b < 0) {
iword = *iwordp++;
b = 31;
}
if (iword & 1) {
*(int *)opos |= mask;
}
opos += owidth;
iword >>= 1;
}
}
static
void fullread (
int file,
char *data,
int nbytes)
{
int bytes_read;
while ((bytes_read = read(file, data, nbytes)) != nbytes) {
if (bytes_read < 0) {
perror ("error while reading standard input");
return;
}
else if (bytes_read == 0) {
fprintf (stderr, "xpr: premature end of file\n");
return;
}
nbytes -= bytes_read;
data += bytes_read;
}
}