xref: /plan9/sys/src/cmd/gs/src/gdev8510.c (revision 593dc095aefb2a85c828727bbfa9da139a49bdf4)
1 /* Copyright (C) 1990, 1992, 1993 Aladdin Enterprises.  All rights reserved.
2 
3   This software is provided AS-IS with no warranty, either express or
4   implied.
5 
6   This software is distributed under license and may not be copied,
7   modified or distributed except as expressly authorized under the terms
8   of the license contained in the file LICENSE in this distribution.
9 
10   For more information about licensing, please refer to
11   http://www.ghostscript.com/licensing/. For information on
12   commercial licensing, go to http://www.artifex.com/licensing/ or
13   contact Artifex Software, Inc., 101 Lucas Valley Road #110,
14   San Rafael, CA  94903, U.S.A., +1(415)492-9861.
15 */
16 
17 /* $Id: gdev8510.c,v 1.7 2004/08/04 23:33:29 stefan Exp $*/
18 /*
19  * C.Itoh M8510 printer driver for ghostscript.
20  *
21  * By Bob Smith <bob@snuffy.penfield.ny.us>
22  */
23 
24 #include "gdevprn.h"
25 
26 /* The device descriptor */
27 private dev_proc_print_page(m8510_print_page);
28 const gx_device_printer far_data gs_m8510_device =
29 	prn_device(prn_std_procs, "m8510",
30 		85,				/* width_10ths, 8.5" */
31 		110,				/* height_10ths, 11" */
32 		160,				/* x_dpi */
33 		144,				/* y_dpi */
34 		0,0,0.5,0,			/* left, bottom, right, and top margins */
35 		1, m8510_print_page);
36 
37 /* ------ forward declarations ------ */
38 
39 private void m8510_output_run(gx_device_printer *pdev,
40 	byte *out, int pass, FILE *prn_stream);
41 
42 /* ------ internal routines ------ */
43 
44 /* Send the page to the printer. */
45 private int
m8510_print_page(gx_device_printer * pdev,FILE * prn_stream)46 m8510_print_page(gx_device_printer *pdev, FILE *prn_stream)
47 {
48 	int line_size = gdev_mem_bytes_per_scan_line((gx_device *)pdev);
49 	byte *in1 = (byte *) gs_malloc(pdev->memory, 8, line_size, "m8510_print_page(in1)");
50 	byte *in2 = (byte *) gs_malloc(pdev->memory, 8, line_size, "m8510_print_page(in2)");
51 	byte *out = (byte *) gs_malloc(pdev->memory, 8, line_size, "m8510_print_page(out)");
52 	int lnum = 0;
53 	int code = 0;
54 	byte *inp, *in_end, *outp;
55 	int i;
56 
57 	if (in1 == 0 || in2 == 0 || out == 0) {
58 		code = gs_error_VMerror;
59 		gs_note_error(code);
60 		goto out;
61 	}
62 
63 	/*
64 	 * Initialize the printer.
65 	 * NLQ mode, proportional print (160x144 dpi).
66 	 * and 16/144" linefeeds.
67 	 */
68 	fwrite("\033m2\033P\033T16", 1, 9, prn_stream);
69 
70 	/* Transfer pixels to printer */
71 	while ( lnum < pdev->height ) {
72 		/* get a raster */
73 		for (i = 7; i >= 0; i--) {
74 			gdev_prn_copy_scan_lines(pdev, lnum, &in1[i*line_size], line_size);
75 			lnum++;
76 			gdev_prn_copy_scan_lines(pdev, lnum, &in2[i*line_size], line_size);
77 			lnum++;
78 		}
79 
80 		/* Transpose the 1st pass of data. */
81 		in_end = in1 + line_size;
82 		for (inp = in1, outp = out; inp < in_end; inp++, outp += 8)
83 			gdev_prn_transpose_8x8(inp, line_size, outp, 1);
84 
85 		/* send the 1st line */
86 		m8510_output_run(pdev, out, 0, prn_stream);
87 
88 		/* Transpose the 2nd pass of data. */
89 		in_end = in2 + line_size;
90 		for (inp = in2, outp = out; inp < in_end; inp++, outp += 8)
91 			gdev_prn_transpose_8x8(inp, line_size, outp, 1);
92 
93 		/* send the 2nd line */
94 		m8510_output_run(pdev, out, 1, prn_stream);
95 	}
96 
97 	/* reset the printer. */
98 	fwrite("\033c1", 1, 3, prn_stream);
99 	fflush(prn_stream);
100 
101 out:;
102 	if (out) gs_free(pdev->memory, (char *) out, 8, line_size, "m8510_print_page(out)");
103 	if (in2) gs_free(pdev->memory, (char *) in2, 8, line_size, "m8510_print_page(in2)");
104 	if (in1) gs_free(pdev->memory, (char *) in1, 8, line_size, "m8510_print_page(in1)");
105 
106 	return code;
107 }
108 
109 private void
m8510_output_run(gx_device_printer * pdev,byte * out,int pass,FILE * prn_stream)110 m8510_output_run(gx_device_printer *pdev,
111 	byte *out, int pass, FILE *prn_stream)
112 {
113 	byte *out_end = out + pdev->width;
114 	char tmp[10];
115 	int count;
116 
117 	/*
118 	 * Remove trailing 0s.
119 	 * out must be a multiple of 8 bytes.
120 	 */
121 	while (out_end > out
122 		&& out_end[-1] == 0
123 		&& out_end[-2] == 0
124 		&& out_end[-3] == 0
125 		&& out_end[-4] == 0
126 		&& out_end[-5] == 0
127 		&& out_end[-6] == 0
128 		&& out_end[-7] == 0
129 		&& out_end[-8] == 0)
130 			out_end -= 8;
131 
132 	/* Transfer the line of data. */
133 	count = out_end - out;
134 	if (count) {
135 		sprintf(tmp, "\033g%03d", count/8);
136 		fwrite(tmp, 1, 5, prn_stream);
137 		fwrite(out, 1, count, prn_stream);
138 		fwrite("\r", 1, 1, prn_stream);
139 	}
140 
141 	if (pass) fwrite("\n", 1, 1, prn_stream);
142 }
143