1 /* sane - Scanner Access Now Easy.
2
3 ScanMaker 3840 Backend
4 Copyright (C) 2005 Earle F. Philhower, III
5 earle@ziplabel.com - http://www.ziplabel.com
6
7 This program is free software; you can redistribute it and/or
8 modify it under the terms of the GNU General Public License as
9 published by the Free Software Foundation; either version 2 of the
10 License, or (at your option) any later version.
11
12 This program is distributed in the hope that it will be useful, but
13 WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
15 General Public License for more details.
16
17 You should have received a copy of the GNU General Public License
18 along with this program. If not, see <https://www.gnu.org/licenses/>.
19
20 As a special exception, the authors of SANE give permission for
21 additional uses of the libraries contained in this release of SANE.
22
23 The exception is that, if you link a SANE library with other files
24 to produce an executable, this does not by itself cause the
25 resulting executable to be covered by the GNU General Public
26 License. Your use of that executable is in no way restricted on
27 account of linking the SANE library code into it.
28
29 This exception does not, however, invalidate any other reasons why
30 the executable file might be covered by the GNU General Public
31 License.
32
33 If you submit changes to SANE to the maintainers to be included in
34 a subsequent release, you agree by submitting the changes that
35 those changes may be distributed with this exception intact.
36
37 If you write modifications of your own for SANE, it is your choice
38 whether to permit this exception to apply to your modifications.
39 If you do not wish that, delete this exception notice.
40
41 */
42
43 #include <stdio.h>
44 #include <stdarg.h>
45 #include "sm3840_lib.h"
46
47 #ifndef BACKENDNAME
48 static void setup_scan (p_usb_dev_handle udev, SM3840_Params * p,
49 char *stname, int raw, int nohead);
50 #else
51 static void setup_scan (p_usb_dev_handle udev, SM3840_Params * p);
52 #endif
53
54
55 #ifndef BACKENDNAME
56
57 #include "sm3840_lib.c"
58
59 int
main(int argc, char *argv[])60 main (int argc, char *argv[])
61 {
62 int i;
63
64 int gray = 0;
65 int dpi = 1200;
66 int bpp16 = 0;
67 int raw = 0;
68 int nohead = 0;
69 double gain = 3.5;
70 int offset = 1800;
71 usb_dev_handle *udev;
72
73 char *stname;
74 double topin, botin, leftin, rightin;
75 int topline, scanlines, leftpix, scanpix;
76
77 stname = NULL;
78 topin = 0.0;
79 botin = 11.7;
80 leftin = 0.0;
81 rightin = 8.5;
82 for (i = 1; i < argc; i++)
83 {
84 if (!strcmp (argv[i], "-300"))
85 dpi = 300;
86 else if (!strcmp (argv[i], "-600"))
87 dpi = 600;
88 else if (!strcmp (argv[i], "-1200"))
89 dpi = 1200;
90 else if (!strcmp (argv[i], "-150"))
91 dpi = 150;
92 else if (!strcmp (argv[i], "-top"))
93 topin = atof (argv[++i]);
94 else if (!strcmp (argv[i], "-bot"))
95 botin = atof (argv[++i]);
96 else if (!strcmp (argv[i], "-left"))
97 leftin = atof (argv[++i]);
98 else if (!strcmp (argv[i], "-right"))
99 rightin = atof (argv[++i]);
100 else if (!strcmp (argv[i], "-gain"))
101 gain = atof (argv[++i]);
102 else if (!strcmp (argv[i], "-offset"))
103 offset = atoi (argv[++i]);
104 else if (!strcmp (argv[i], "-gray"))
105 gray = 1;
106 else if (!strcmp (argv[i], "-16bpp"))
107 bpp16 = 1;
108 else if (!strcmp (argv[i], "-raw"))
109 raw = 1;
110 else if (!strcmp (argv[i], "-nohead"))
111 nohead = 1;
112 else
113 stname = argv[i];
114 }
115
116 SM3840_Params params;
117 params.gray = gray;
118 params.dpi = dpi;
119 params.bpp = bpp16 ? 16 : 8;
120 params.gain = gain;
121 params.offset = offset;
122 params.lamp = 15;
123 params.top = topin;
124 params.left = leftin;
125 params.height = botin - topin;
126 params.width = rightin - leftin;
127
128 prepare_params (¶ms);
129 udev = find_device (0x05da, 0x30d4); /* 3840 */
130 if (!udev)
131 udev = find_device (0x05da, 0x30cf); /* 4800 */
132 if (!udev)
133 fprintf (stderr, "Unable to open scanner.\n");
134 else
135 setup_scan (udev, ¶ms, stname, raw, nohead);
136
137 return 0;
138 }
139 #endif
140
141 #ifndef BACKENDNAME
142 static void
setup_scan(p_usb_dev_handle udev, SM3840_Params * p, char *stname, int raw, int nohead)143 setup_scan (p_usb_dev_handle udev, SM3840_Params * p,
144 char *stname, int raw, int nohead)
145 #else
146 static void
147 setup_scan (p_usb_dev_handle udev, SM3840_Params * p)
148 #endif
149 {
150 int gray = p->gray ? 1 : 0;
151 int dpi = p->dpi;
152 int bpp16 = (p->bpp == 16) ? 1 : 0;
153 double gain = p->gain;
154 int offset = p->offset;
155 int topline = p->topline;
156 int scanlines = p->scanlines;
157 int leftpix = p->leftpix;
158 int scanpix = p->scanpix;
159 unsigned char hello[2] = { 0x55, 0xaa };
160 unsigned char howdy[3];
161 unsigned short *whitebalance;
162 int whitebalancesize = (dpi == 1200) ? 12672 : 6528;
163 unsigned short *whitemap;
164 int whitemapsize = (dpi == 1200) ? 29282 : 14642;
165 unsigned short *whitescan;
166 unsigned short *lightmap;
167 unsigned int topreg, botreg;
168 int redreg, greenreg, bluereg, donered, donegreen, doneblue;
169 int rgreg = 0x00;
170 int ggreg = 0x00;
171 int bgreg = 0x00;
172 int i, j;
173 int red, green, blue;
174 unsigned char rd_byte;
175 unsigned short GRAYMASK = 0xc000;
176
177
178 #ifndef BACKENDNAME
179 char fname[64];
180 char head[128];
181
182 usb_set_configuration (udev, 1);
183 usb_claim_interface (udev, 0);
184 usb_clear_halt (udev, 1);
185 usb_clear_halt (udev, 2);
186 usb_clear_halt (udev, 3);
187 #endif
188 DBG (2, "params.gray = %d;\n", p->gray);
189 DBG (2, "params.dpi = %d\n", p->dpi);
190 DBG (2, "params.bpp = %d\n", p->bpp);
191 DBG (2, "params.gain = %f\n", p->gain);
192 DBG (2, "params.offset = %d\n", p->offset);
193 DBG (2, "params.lamp = %d\n", p->lamp);
194 DBG (2, "params.top = %f\n", p->top);
195 DBG (2, "params.left = %f\n", p->left);
196 DBG (2, "params.height = %f\n", p->height);
197 DBG (2, "params.width = %f\n", p->width);
198
199 DBG (2, "params.topline = %d\n", p->topline);
200 DBG (2, "params.scanlines = %d\n", p->scanlines);
201 DBG (2, "params.leftpix = %d\n", p->leftpix);
202 DBG (2, "params.scanpix = %d\n", p->scanpix);
203
204 DBG (2, "params.linelen = %d\n", p->linelen);
205
206 reset_scanner (udev);
207
208 idle_ab (udev);
209 write_regs (udev, 4, 0x83, 0x00, 0xa3, 0x00, 0xa4, 0x00, 0x97, 0x0a);
210 write_vctl (udev, 0x0c, 0x0004, 0x008b, 0x00);
211 read_vctl (udev, 0x0c, 0x0007, 0x0000, &rd_byte);
212 write_regs (udev, 1, 0x97, 0x0b);
213 write_vctl (udev, 0x0c, 0x0004, 0x008b, 0x00);
214 read_vctl (udev, 0x0c, 0x0007, 0x0000, &rd_byte);
215 write_regs (udev, 1, 0x97, 0x0f);
216 write_vctl (udev, 0x0c, 0x0004, 0x008b, 0x00);
217 read_vctl (udev, 0x0c, 0x0007, 0x0000, &rd_byte);
218 write_regs (udev, 1, 0x97, 0x05);
219 write_vctl (udev, 0x0b, 0x0004, 0x008b, 0x00);
220 read_vctl (udev, 0x0c, 0x0007, 0x0000, &rd_byte);
221 write_regs (udev, 7, 0xa8, 0x80, 0x83, 0xa2, 0x85, 0x01, 0x83, 0x82, 0x85,
222 0x00, 0x83, 0x00, 0x93, 0x00);
223 write_regs (udev, 1, 0xa8, 0x80);
224 write_regs (udev, 4, 0x83, 0x00, 0xa3, 0x00, 0xa4, 0x00, 0x97, 0x0a);
225 write_vctl (udev, 0x0c, 0x0004, 0x008b, 0x00);
226 read_vctl (udev, 0x0c, 0x0007, 0x0000, &rd_byte);
227 write_regs (udev, 1, 0x97, 0x0b);
228 write_vctl (udev, 0x0c, 0x0004, 0x008b, 0x00);
229 read_vctl (udev, 0x0c, 0x0007, 0x0000, &rd_byte);
230 write_regs (udev, 1, 0x97, 0x0f);
231 write_vctl (udev, 0x0c, 0x0004, 0x008b, 0x00);
232 read_vctl (udev, 0x0c, 0x0007, 0x0000, &rd_byte);
233 write_regs (udev, 1, 0x97, 0x05);
234 write_vctl (udev, 0x0c, 0x0004, 0x008b, 0x00);
235 read_vctl (udev, 0x0c, 0x0007, 0x0000, &rd_byte);
236 write_regs (udev, 4, 0x83, 0x20, 0x8d, 0xfe, 0x83, 0x00, 0x8d, 0xff);
237 write_regs (udev, 1, 0x97, 0x00);
238 write_vctl (udev, 0x0c, 0x0004, 0x008b, 0x00);
239 read_vctl (udev, 0x0c, 0x0007, 0x0000, &rd_byte);
240 write_regs (udev, 8, 0x80, 0x00, 0x84, 0x00, 0xbe, 0x00, 0xc0, 0x00, 0x86,
241 0x00, 0x89, 0x00, 0x94, 0x00, 0x01, 0x02);
242 write_vctl (udev, 0x0c, 0x00c0, 0x8406, 0x00);
243 write_vctl (udev, 0x0c, 0x00c0, 0x0406, 0x00);
244 write_regs (udev, 1, 0x94, 0x51);
245 write_regs (udev, 1, 0xb0, 0x00);
246 write_regs (udev, 1, 0xb1, 0x00);
247 write_regs (udev, 1, 0xb2, 0x00);
248 write_regs (udev, 1, 0xb3, 0x00);
249 write_regs (udev, 1, 0xb4, 0x10);
250 write_regs (udev, 1, 0xb5, 0x1f);
251 write_regs (udev, 1, 0xb0, 0x00);
252 write_regs (udev, 1, 0xb1, 0x00);
253 write_regs (udev, 1, 0xb2, 0x00);
254 write_vctl (udev, 0x0c, 0x0002, 0x0002, 0x00);
255 usb_bulk_write (udev, 2, hello, 2, wr_timeout);
256 write_regs (udev, 1, 0xb0, 0x00);
257 write_regs (udev, 1, 0xb1, 0x00);
258 write_regs (udev, 1, 0xb2, 0x00);
259 write_vctl (udev, 0x0c, 0x0003, 0x0003, 0x00);
260 usb_bulk_read (udev, 1, howdy, 3, rd_timeout);
261 write_regs (udev, 4, 0x83, 0x00, 0xa3, 0x00, 0xa4, 0x00, 0x97, 0x0a);
262 write_vctl (udev, 0x0c, 0x0004, 0x008b, 0x00);
263 read_vctl (udev, 0x0c, 0x0007, 0x0000, &rd_byte);
264 write_regs (udev, 1, 0x97, 0x0b);
265 write_vctl (udev, 0x0c, 0x0004, 0x008b, 0x00);
266 read_vctl (udev, 0x0c, 0x0007, 0x0000, &rd_byte);
267 write_regs (udev, 1, 0x97, 0x0f);
268 write_vctl (udev, 0x0c, 0x0004, 0x008b, 0x00);
269 read_vctl (udev, 0x0c, 0x0007, 0x0000, &rd_byte);
270 write_regs (udev, 1, 0x97, 0x05);
271 write_vctl (udev, 0x0c, 0x0004, 0x008b, 0x00);
272 read_vctl (udev, 0x0c, 0x0007, 0x0000, &rd_byte);
273 write_regs (udev, 4, 0x83, 0x20, 0x8d, 0xfe, 0x83, 0x00, 0x8d, 0xff);
274 write_regs (udev, 1, 0x97, 0x00);
275 write_vctl (udev, 0x0c, 0x0004, 0x008b, 0x00);
276 read_vctl (udev, 0x0c, 0x0007, 0x0000, &rd_byte);
277 write_regs (udev, 8, 0x80, 0x00, 0x84, 0x00, 0xbe, 0x00, 0xc0, 0x00, 0x86,
278 0x00, 0x89, 0x00, 0x94, 0x00, 0x01, 0x02);
279 write_vctl (udev, 0x0c, 0x00c0, 0x8406, 0x00);
280 write_vctl (udev, 0x0c, 0x00c0, 0x0406, 0x00);
281 write_regs (udev, 16, 0xbe, 0x18, 0x80, 0x00, 0x84, 0x00, 0x89, 0x00, 0x88,
282 0x00, 0x86, 0x00, 0x90, 0x00, 0xc1, 0x00, 0xc2, 0x00, 0xc3,
283 0x00, 0xc4, 0x00, 0xc5, 0x00, 0xc6, 0x00, 0xc7, 0x00, 0xc8,
284 0x00, 0xc0, 0x00);
285 write_regs (udev, 4, 0x83, 0x20, 0x8d, 0xff, 0x83, 0x00, 0x8d, 0xff);
286 write_regs (udev, 5, 0x83, 0x00, 0xa3, 0xff, 0xa4, 0xff, 0xa1, 0xff, 0xa2,
287 0xf7);
288 write_regs (udev, 4, 0x83, 0x22, 0x87, 0x01, 0x83, 0x02, 0x87, 0x16);
289 write_regs (udev, 11, 0xa0, 0x00, 0x9c, 0x00, 0x9f, 0x00, 0x9d, 0x00, 0x9e,
290 0x00, 0xa0, 0x00, 0xce, 0x0c, 0x83, 0x20, 0xa5, 0x00, 0xa6,
291 0x00, 0xa7, 0x00);
292
293 set_gain_black (udev, 0x01, 0x01, 0x01, 0xaa, 0xaa, 0xaa);
294
295 write_regs (udev, 16, 0x9b, 0x00, 0x98, 0x00, 0x99, 0x00, 0x9a, 0x00, 0x9b,
296 0x01, 0x98, 0x00, 0x99, 0x00, 0x9a, 0x00, 0x9b, 0x02, 0x98,
297 0x00, 0x99, 0x00, 0x9a, 0x00, 0x9b, 0x03, 0x98, 0x00, 0x99,
298 0x00, 0x9a, 0x00);
299 write_regs (udev, 4, 0x83, 0xa2, 0x85, 0x98, 0x83, 0x82, 0x85, 0x3a);
300 write_regs (udev, 1, 0x9d, 0x80);
301 write_regs (udev, 1, 0x9d, 0x00);
302
303 if (dpi == 1200)
304 write_regs (udev, 1, 0x94, 0x51);
305 else
306 write_regs (udev, 1, 0x94, 0x61);
307
308 whitemap = (unsigned short *) malloc (whitemapsize);
309
310 set_lightmap_white (whitemap, dpi, 0);
311 if (dpi == 1200)
312 write_regs (udev, 6, 0xb0, 0x00, 0xb1, 0x80, 0xb2, 0x06, 0xb3, 0xff, 0xb4,
313 0xff, 0xb5, 0x06);
314 else
315 write_regs (udev, 6, 0xb0, 0x00, 0xb1, 0x40, 0xb2, 0x07, 0xb3, 0xff, 0xb4,
316 0x7f, 0xb5, 0x07);
317 write_vctl (udev, 0x0c, 0x0002, whitemapsize, 0x00);
318 usb_bulk_write (udev, 2, (unsigned char *) whitemap, whitemapsize,
319 wr_timeout);
320
321 set_lightmap_white (whitemap, dpi, 1);
322 if (dpi == 1200)
323 write_regs (udev, 6, 0xb0, 0x00, 0xb1, 0x00, 0xb2, 0x07, 0xb3, 0xff, 0xb4,
324 0x7f, 0xb5, 0x07);
325 else
326 write_regs (udev, 6, 0xb0, 0x00, 0xb1, 0x80, 0xb2, 0x07, 0xb3, 0xff, 0xb4,
327 0xbf, 0xb5, 0x07);
328 write_vctl (udev, 0x0c, 0x0002, whitemapsize, 0x00);
329 usb_bulk_write (udev, 2, (unsigned char *) whitemap, whitemapsize,
330 wr_timeout);
331
332 set_lightmap_white (whitemap, dpi, 2);
333 if (dpi == 1200)
334 write_regs (udev, 6, 0xb0, 0x00, 0xb1, 0x80, 0xb2, 0x07, 0xb3, 0xff, 0xb4,
335 0xff, 0xb5, 0x07);
336 else
337 write_regs (udev, 6, 0xb0, 0x00, 0xb1, 0xc0, 0xb2, 0x07, 0xb3, 0xff, 0xb4,
338 0xff, 0xb5, 0x07);
339 write_vctl (udev, 0x0c, 0x0002, whitemapsize, 0x00);
340 usb_bulk_write (udev, 2, (unsigned char *) whitemap, whitemapsize,
341 wr_timeout);
342
343 free (whitemap);
344
345 /* Move to head... */
346 idle_ab (udev);
347 write_regs (udev, 1, 0x97, 0x00);
348 idle_ab (udev);
349 write_regs (udev, 16, 0xbe, 0x18, 0x80, 0x00, 0x84, 0x00, 0x89, 0x00, 0x88,
350 0x00, 0x86, 0x00, 0x90, 0x00, 0xc1, 0x00, 0xc2, 0x00, 0xc3,
351 0x00, 0xc4, 0x00, 0xc5, 0x00, 0xc6, 0x00, 0xc7, 0x00, 0xc8,
352 0x00, 0xc0, 0x00);
353 idle_ab (udev);
354 write_regs (udev, 16, 0x84, 0x94, 0x80, 0xd1, 0x80, 0xc1, 0x82, 0x7f, 0xcf,
355 0x04, 0xc1, 0x02, 0xc2, 0x00, 0xc3, 0x06, 0xc4, 0xff, 0xc5,
356 0x40, 0xc6, 0x8c, 0xc7, 0xdc, 0xc8, 0x20, 0xc0, 0x72, 0x89,
357 0xff, 0x86, 0xff);
358 poll1 (udev);
359
360 write_regs (udev, 4, 0x83, 0xa2, 0x85, 0x01, 0x83, 0x82, 0x85, 0x00);
361 write_regs (udev, 1, 0x9d, 0x80);
362 write_regs (udev, 1, 0x9d, 0x00);
363 if (dpi == 1200)
364 write_regs (udev, 10, 0xb0, 0x00, 0xb1, 0x00, 0xb2, 0x00, 0xb3, 0xff,
365 0xb4, 0xff, 0xb5, 0x03, 0xb6, 0x01, 0xb7, 0x00, 0xb8, 0x77,
366 0xb9, 0x1e);
367 else
368 write_regs (udev, 10, 0xb0, 0x00, 0xb1, 0x00, 0xb2, 0x00, 0xb3, 0xff,
369 0xb4, 0xff, 0xb5, 0x03, 0xb6, 0x01, 0xb7, 0x00, 0xb8, 0x3b,
370 0xb9, 0x1f);
371 write_regs (udev, 5, 0xc0, 0x00, 0x84, 0x00, 0x80, 0xa1, 0xcf, 0x04, 0x82,
372 0x00);
373 if (dpi == 1200)
374 write_regs (udev, 18, 0x83, 0xa2, 0x85, 0x02, 0x83, 0x82, 0x85, 0x00,
375 0xbc, 0x01, 0xbd, 0x01, 0x88, 0xa4, 0xc1, 0x02, 0xc2, 0x00,
376 0xc3, 0x02, 0xc4, 0x01, 0xc5, 0x01, 0xc6, 0xa3, 0xc7, 0xa4,
377 0xc8, 0x04, 0xc0, 0xd2, 0x89, 0x05, 0x86, 0x00);
378 else
379 write_regs (udev, 18, 0x83, 0xa2, 0x85, 0x04, 0x83, 0x82, 0x85, 0x00,
380 0xbc, 0x01, 0xbd, 0x01, 0x88, 0xd0, 0xc1, 0x01, 0xc2, 0x00,
381 0xc3, 0x04, 0xc4, 0x01, 0xc5, 0x01, 0xc6, 0xcf, 0xc7, 0xd0,
382 0xc8, 0x14, 0xc0, 0xd1, 0x89, 0x0a, 0x86, 0x00);
383 write_regs (udev, 8, 0xbb, 0x01, 0x9b, 0x24, 0x8b, 0x00, 0x8e, 0x80, 0xbf,
384 0x00, 0x90, 0x40, 0x91, 0x00, 0x83, 0x82);
385 write_regs (udev, 1, 0xbe, 0x0d);
386 write_vctl (udev, 0x0c, 0x0003, 0x0001, 0x00);
387 whitebalance = (unsigned short *) malloc (whitebalancesize);
388 usb_bulk_read (udev, 1, &rd_byte, 1, rd_timeout);
389 write_vctl (udev, 0x0c, 0x0001, 0x0000, 0x00);
390 usb_bulk_read (udev, 1, (unsigned char *) whitebalance, whitebalancesize,
391 rd_timeout);
392 write_regs (udev, 2, 0xbe, 0x00, 0x84, 0x00);
393 write_vctl (udev, 0x0c, 0x00c0, 0x8406, 0x00);
394 write_vctl (udev, 0x0c, 0x00c0, 0x0406, 0x00);
395 redreg = greenreg = bluereg = 0x80;
396 red = green = blue = 0;
397 donered = donegreen = doneblue = 0;
398 DBG (2, "setting blackpoint\n");
399 for (j = 0; (j < 16) && !(donered && donegreen && doneblue); j++)
400 {
401 set_gain_black (udev, 0x01, 0x01, 0x01, redreg, greenreg, bluereg);
402
403 if (dpi == 1200)
404 write_regs (udev, 10, 0xb0, 0x00, 0xb1, 0x00, 0xb2, 0x00, 0xb3, 0xff,
405 0xb4, 0xff, 0xb5, 0x03, 0xb6, 0x01, 0xb7, 0x00, 0xb8,
406 0x77, 0xb9, 0x1e);
407 else
408 write_regs (udev, 10, 0xb0, 0x00, 0xb1, 0x00, 0xb2, 0x00, 0xb3, 0xff,
409 0xb4, 0xff, 0xb5, 0x03, 0xb6, 0x01, 0xb7, 0x00, 0xb8,
410 0x3b, 0xb9, 0x1f);
411 write_regs (udev, 8, 0xbb, 0x01, 0x9b, 0x24, 0x8b, 0x00, 0x8e, 0x80,
412 0xbf, 0x00, 0x90, 0x40, 0x91, 0x00, 0x83, 0x82);
413 write_regs (udev, 1, 0xbe, 0x0d);
414 write_vctl (udev, 0x0c, 0x0003, 0x0001, 0x00);
415 usb_bulk_read (udev, 1, &rd_byte, 1, rd_timeout);
416 write_vctl (udev, 0x0c, 0x0001, 0x0000, 0x00);
417 usb_bulk_read (udev, 1, (unsigned char *) whitebalance,
418 whitebalancesize, rd_timeout);
419 fix_endian_short (whitebalance, whitebalancesize/2);
420 if (!donered)
421 {
422 red = (whitebalance[0] + whitebalance[3] + whitebalance[6]) / 3;
423 if (red > 0x1000)
424 redreg += 0x10;
425 else if (red > 0x500)
426 redreg += 0x08;
427 else if (red > 0x0010)
428 redreg++;
429 else
430 donered = 1;
431 }
432 if (!donegreen)
433 {
434 green = (whitebalance[1] + whitebalance[4] + whitebalance[7]) / 3;
435 if (green > 0x1000)
436 greenreg += 0x10;
437 else if (green > 0x0500)
438 greenreg += 0x08;
439 else if (green > 0x0010)
440 greenreg++;
441 else
442 donegreen = 1;
443 }
444 if (!doneblue)
445 {
446 blue = (whitebalance[2] + whitebalance[5] + whitebalance[8]) / 3;
447 if (blue > 0x1000)
448 bluereg += 0x10;
449 else if (blue > 0x0500)
450 bluereg += 0x08;
451 else if (blue > 0x0010)
452 bluereg++;
453 else
454 doneblue = 1;
455 }
456 DBG (2, "red=%d(%d)%02x, green=%d(%d)%02x, blue=%d(%d)%02x\n",
457 red, donered, redreg, green, donegreen, greenreg,
458 blue, doneblue, bluereg);
459 write_regs (udev, 2, 0xbe, 0x00, 0x84, 0x00);
460 write_vctl (udev, 0x0c, 0x00c0, 0x8406, 0x00);
461 write_vctl (udev, 0x0c, 0x00c0, 0x0406, 0x00);
462 }
463 DBG (2, "setting whitepoint\n");
464 donegreen = donered = doneblue = 0;
465 for (j = 0; (j < 16) && !(donered && donegreen && doneblue); j++)
466 {
467 set_gain_black (udev, rgreg, ggreg, bgreg, redreg, greenreg, bluereg);
468
469 if (dpi == 1200)
470 idle_ab (udev);
471 write_regs (udev, 10, 0xb0, 0x00, 0xb1, 0x00, 0xb2, 0x00, 0xb3, 0xff,
472 0xb4, 0xff, 0xb5, 0x03, 0xb6, 0x01, 0xb7, 0x00, 0xb8, 0x3b,
473 0xb9, 0x1f);
474 if (dpi == 1200)
475 idle_ab (udev);
476 write_regs (udev, 8, 0xbb, 0x01, 0x9b, 0x24, 0x8b, 0x00, 0x8e, 0x80,
477 0xbf, 0x00, 0x90, 0x40, 0x91, 0x00, 0x83, 0x82);
478 write_regs (udev, 1, 0xbe, 0x0d);
479 write_vctl (udev, 0x0c, 0x0003, 0x0001, 0x00);
480 usb_bulk_read (udev, 1, &rd_byte, 1, rd_timeout);
481 write_vctl (udev, 0x0c, 0x0001, 0x0000, 0x00);
482 usb_bulk_read (udev, 1, (unsigned char *) whitebalance,
483 whitebalancesize, rd_timeout);
484 fix_endian_short (whitebalance, whitebalancesize/2);
485 if (!donered)
486 {
487 red =
488 (whitebalance[180 * 3 + 0] + whitebalance[180 * 3 + 3] +
489 whitebalance[180 * 3 + 6]) / 3;
490 if (red < 0x5000)
491 rgreg += 0x02;
492 else if (red < 0x8000)
493 rgreg += 0x01;
494 else
495 donered = 1;
496 }
497 if (!donegreen)
498 {
499 green =
500 (whitebalance[180 * 3 + 1] + whitebalance[180 * 3 + 4] +
501 whitebalance[180 * 3 + 7]) / 3;
502 if (green < 0x5000)
503 ggreg += 0x02;
504 else if (green < 0x8000)
505 ggreg += 0x01;
506 else
507 donegreen = 1;
508 }
509 if (!doneblue)
510 {
511 blue =
512 (whitebalance[180 * 3 + 2] + whitebalance[180 * 3 + 5] +
513 whitebalance[180 * 3 + 8]) / 3;
514 if (blue < 0x5000)
515 bgreg += 0x02;
516 else if (blue < 0x8000)
517 bgreg += 0x01;
518 else
519 doneblue = 1;
520 }
521 DBG (2, "red=%d(%d)%02x, green=%d(%d)%02x, blue=%d(%d)%02x\n",
522 red, donered, rgreg, green, donegreen, ggreg, blue, doneblue,
523 bgreg);
524 write_regs (udev, 2, 0xbe, 0x00, 0x84, 0x00);
525 write_vctl (udev, 0x0c, 0x00c0, 0x8406, 0x00);
526 write_vctl (udev, 0x0c, 0x00c0, 0x0406, 0x00);
527 }
528 free (whitebalance);
529
530 /* One step down for optimal contrast... */
531 if (rgreg)
532 rgreg--;
533 if (bgreg)
534 bgreg--;
535 if (ggreg)
536 ggreg--;
537
538
539 write_regs (udev, 8, 0x80, 0x00, 0x84, 0x00, 0xbe, 0x00, 0xc0, 0x00, 0x86,
540 0x00, 0x89, 0x00, 0x94, 0x00, 0x01, 0x02);
541 write_vctl (udev, 0x0c, 0x00c0, 0x8406, 0x00);
542 write_vctl (udev, 0x0c, 0x00c0, 0x0406, 0x00);
543 write_regs (udev, 16, 0xbe, 0x18, 0x80, 0x00, 0x84, 0x00, 0x89, 0x00, 0x88,
544 0x00, 0x86, 0x00, 0x90, 0x00, 0xc1, 0x00, 0xc2, 0x00, 0xc3,
545 0x00, 0xc4, 0x00, 0xc5, 0x00, 0xc6, 0x00, 0xc7, 0x00, 0xc8,
546 0x00, 0xc0, 0x00);
547 write_regs (udev, 4, 0x83, 0x20, 0x8d, 0xff, 0x83, 0x00, 0x8d, 0xff);
548 write_regs (udev, 5, 0x83, 0x00, 0xa3, 0xff, 0xa4, 0xff, 0xa1, 0xff, 0xa2,
549 0xf7);
550 write_regs (udev, 4, 0x83, 0x22, 0x87, 0x01, 0x83, 0x02, 0x87, 0x16);
551 write_regs (udev, 11, 0xa0, 0x00, 0x9c, 0x00, 0x9f, 0x00, 0x9d, 0x00, 0x9e,
552 0x00, 0xa0, 0x00, 0xce, 0x0c, 0x83, 0x20, 0xa5, 0x00, 0xa6,
553 0x00, 0xa7, 0x00);
554 set_gain_black (udev, rgreg, ggreg, bgreg, redreg, greenreg, bluereg);
555
556 write_regs (udev, 16, 0x9b, 0x00, 0x98, 0x00, 0x99, 0x00, 0x9a, 0x00, 0x9b,
557 0x01, 0x98, 0x00, 0x99, 0x00, 0x9a, 0x00, 0x9b, 0x02, 0x98,
558 0x00, 0x99, 0x00, 0x9a, 0x00, 0x9b, 0x03, 0x98, 0x00, 0x99,
559 0x00, 0x9a, 0x00);
560 write_regs (udev, 4, 0x83, 0xa2, 0x85, 0x98, 0x83, 0x82, 0x85, 0x3a);
561 write_regs (udev, 1, 0x9d, 0x80);
562 write_regs (udev, 1, 0x9d, 0x00);
563 if (dpi == 1200)
564 write_regs (udev, 1, 0x94, 0x71);
565 else
566 write_regs (udev, 1, 0x94, 0x61);
567
568 write_regs (udev, 4, 0x83, 0xa2, 0x85, 0x01, 0x83, 0x82, 0x85, 0x00);
569 write_regs (udev, 1, 0x9d, 0x80);
570 write_regs (udev, 1, 0x9d, 0x00);
571 if (dpi == 1200)
572 write_regs (udev, 10, 0xb0, 0x00, 0xb1, 0x00, 0xb2, 0x00, 0xb3, 0xff,
573 0xb4, 0xff, 0xb5, 0x03, 0xb6, 0x01, 0xb7, 0x00, 0xb8, 0xbf,
574 0xb9, 0x17);
575 else
576 write_regs (udev, 10, 0xb0, 0x00, 0xb1, 0x00, 0xb2, 0x00, 0xb3, 0xff,
577 0xb4, 0xff, 0xb5, 0x03, 0xb6, 0x01, 0xb7, 0x00, 0xb8, 0xdf,
578 0xb9, 0x1b);
579 write_regs (udev, 6, 0xc0, 0x00, 0x84, 0x00, 0x84, 0xb4, 0x80, 0xe1, 0xcf,
580 0x04, 0x82, 0x00);
581 if (dpi == 1200)
582 write_regs (udev, 18, 0x83, 0xa2, 0x85, 0x02, 0x83, 0x82, 0x85, 0x00,
583 0xbc, 0x20, 0xbd, 0x08, 0x88, 0xa4, 0xc1, 0x02, 0xc2, 0x00,
584 0xc3, 0x02, 0xc4, 0x20, 0xc5, 0x08, 0xc6, 0x96, 0xc7, 0xa4,
585 0xc8, 0x06, 0xc0, 0xd2, 0x89, 0x24, 0x86, 0x01);
586 else
587 write_regs (udev, 18, 0x83, 0xa2, 0x85, 0x04, 0x83, 0x82, 0x85, 0x00,
588 0xbc, 0x20, 0xbd, 0x10, 0x88, 0xd0, 0xc1, 0x01, 0xc2, 0x00,
589 0xc3, 0x04, 0xc4, 0x20, 0xc5, 0x10, 0xc6, 0xc3, 0xc7, 0xd0,
590 0xc8, 0x1c, 0xc0, 0xd1, 0x89, 0x24, 0x86, 0x01);
591 write_regs (udev, 8, 0xbb, 0x05, 0x9b, 0x24, 0x8b, 0x00, 0x8e, 0x80, 0xbf,
592 0x00, 0x90, 0x40, 0x91, 0x00, 0x83, 0x82);
593 write_regs (udev, 1, 0xbe, 0x1d);
594 write_vctl (udev, 0x0c, 0x0003, 0x0001, 0x00);
595 usb_bulk_read (udev, 1, &rd_byte, 1, rd_timeout);
596 write_vctl (udev, 0x0c, 0x0001, 0x0000, 0x00);
597 record_mem (udev, (unsigned char **) (void *)&whitescan,
598 (5632 * 2 * 3 * (dpi == 1200 ? 2 : 1)) * 4);
599 fix_endian_short (whitescan, (5632 * 2 * 3 * (dpi == 1200 ? 2 : 1)) * 2);
600 write_regs (udev, 5, 0x83, 0x00, 0xa3, 0xff, 0xa4, 0xff, 0xa1, 0xff, 0xa2,
601 0xff);
602 write_vctl (udev, 0x0c, 0x0001, 0x0000, 0x00);
603 write_regs (udev, 2, 0xbe, 0x00, 0x84, 0x00);
604 write_vctl (udev, 0x0c, 0x00c0, 0x8406, 0x00);
605 write_vctl (udev, 0x0c, 0x00c0, 0x0406, 0x00);
606 write_regs (udev, 4, 0x83, 0x00, 0xa3, 0x00, 0xa4, 0x00, 0x97, 0x0a);
607 write_vctl (udev, 0x0c, 0x0004, 0x008b, 0x00);
608 read_vctl (udev, 0x0c, 0x0007, 0x0000, &rd_byte);
609 write_regs (udev, 1, 0x97, 0x0b);
610 write_vctl (udev, 0x0c, 0x0004, 0x008b, 0x00);
611 read_vctl (udev, 0x0c, 0x0007, 0x0000, &rd_byte);
612 write_regs (udev, 1, 0x97, 0x0f);
613 write_vctl (udev, 0x0c, 0x0004, 0x008b, 0x00);
614 read_vctl (udev, 0x0c, 0x0007, 0x0000, &rd_byte);
615 write_regs (udev, 1, 0x97, 0x05);
616 write_vctl (udev, 0x0c, 0x0004, 0x008b, 0x00);
617 read_vctl (udev, 0x0c, 0x0007, 0x0000, &rd_byte);
618 write_regs (udev, 4, 0x83, 0x20, 0x8d, 0xff, 0x83, 0x00, 0x8d, 0xff);
619 write_regs (udev, 1, 0x97, 0x00);
620 write_vctl (udev, 0x0c, 0x0004, 0x008b, 0x00);
621 read_vctl (udev, 0x0c, 0x0007, 0x0000, &rd_byte);
622 write_regs (udev, 1, 0x97, 0x00);
623 write_vctl (udev, 0x0c, 0x0004, 0x008b, 0x00);
624 read_vctl (udev, 0x0c, 0x0007, 0x0000, &rd_byte);
625 write_regs (udev, 16, 0xbe, 0x18, 0x80, 0x00, 0x84, 0x00, 0x89, 0x00, 0x88,
626 0x00, 0x86, 0x00, 0x90, 0x00, 0xc1, 0x00, 0xc2, 0x00, 0xc3,
627 0x00, 0xc4, 0x00, 0xc5, 0x00, 0xc6, 0x00, 0xc7, 0x00, 0xc8,
628 0x00, 0xc0, 0x00);
629 write_regs (udev, 16, 0x84, 0x94, 0x80, 0xd1, 0x80, 0xc1, 0x82, 0x7f, 0xcf,
630 0x04, 0xc1, 0x02, 0xc2, 0x00, 0xc3, 0x06, 0xc4, 0xff, 0xc5,
631 0x40, 0xc6, 0x8c, 0xc7, 0xdc, 0xc8, 0x20, 0xc0, 0x72, 0x89,
632 0xff, 0x86, 0xff);
633 poll1 (udev);
634
635 /* ready scan position */
636 /* 1/3" of unscannable area at top... */
637 if (dpi == 300)
638 topreg = 120 * 4;
639 else if (dpi == 600)
640 topreg = 139 * 4;
641 else if (dpi == 1200)
642 topreg = 152 * 4;
643 else /*if (dpi == 150) */
644 topreg = 120 * 4;
645 topreg += topline * (1200 / dpi);
646
647 write_regs (udev, 16, 0xbe, 0x18, 0x80, 0x00, 0x84, 0x00, 0x89, 0x00, 0x88,
648 0x00, 0x86, 0x00, 0x90, 0x00, 0xc1, 0x00, 0xc2, 0x00, 0xc3,
649 0x00, 0xc4, 0x00, 0xc5, 0x00, 0xc6, 0x00, 0xc7, 0x00, 0xc8,
650 0x00, 0xc0, 0x00);
651 write_regs (udev, 14, 0x84, 0xb4, 0x80, 0xe1, 0xcf, 0x04, 0xc1, 0x02, 0xc2,
652 0x00, 0xc3, 0x07, 0xc4, 0xff, 0xc5, 0x40, 0xc6, 0x8c, 0xc7,
653 0xdc, 0xc8, 0x20, 0xc0, 0x72, 0x89, topreg & 255, 0x86,
654 255 & (topreg >> 8));
655 write_regs (udev, 1, 0x97, 0x00);
656 poll2 (udev);
657
658 write_regs (udev, 8, 0x80, 0x00, 0x84, 0x00, 0xbe, 0x00, 0xc0, 0x00, 0x86,
659 0x00, 0x89, 0x00, 0x94, 0x00, 0x01, 0x02);
660 write_vctl (udev, 0x0c, 0x00c0, 0x8406, 0x00);
661 write_vctl (udev, 0x0c, 0x00c0, 0x0406, 0x00);
662 write_regs (udev, 16, 0xbe, 0x18, 0x80, 0x00, 0x84, 0x00, 0x89, 0x00, 0x88,
663 0x00, 0x86, 0x00, 0x90, 0x00, 0xc1, 0x00, 0xc2, 0x00, 0xc3,
664 0x00, 0xc4, 0x00, 0xc5, 0x00, 0xc6, 0x00, 0xc7, 0x00, 0xc8,
665 0x00, 0xc0, 0x00);
666 if (dpi == 1200)
667 write_regs (udev, 4, 0x83, 0x20, 0x8d, 0x24, 0x83, 0x00, 0x8d, 0xff);
668 else
669 write_regs (udev, 4, 0x83, 0x20, 0x8d, 0xff, 0x83, 0x00, 0x8d, 0xff);
670 if (dpi != 1200)
671 write_regs (udev, 5, 0x83, 0x00, 0xa3, 0xff, 0xa4, 0xff, 0xa1, 0xff, 0xa2,
672 0xf7);
673 if (dpi == 1200)
674 write_regs (udev, 4, 0x83, 0x22, 0x87, 0x01, 0x83, 0x02, 0x87, 0x2c);
675 else
676 write_regs (udev, 4, 0x83, 0x22, 0x87, 0x01, 0x83, 0x02, 0x87, 0x16);
677 if (dpi == 1200)
678 write_regs (udev, 11, 0xa0, 0x00, 0x9c, 0x00, 0x9f, 0x40, 0x9d, 0x00,
679 0x9e, 0x00, 0xa0, 0x00, 0xce, 0x0c, 0x83, 0x20, 0xa5, 0x00,
680 0xa6, 0x00, 0xa7, 0x00);
681 else
682 write_regs (udev, 11, 0xa0, 0x00, 0x9c, 0x00, 0x9f, 0x00, 0x9d, 0x00,
683 0x9e, 0x00, 0xa0, 0x00, 0xce, 0x0c, 0x83, 0x20, 0xa5, 0x00,
684 0xa6, 0x00, 0xa7, 0x00);
685
686 set_gain_black (udev, rgreg, ggreg, bgreg, redreg, greenreg, bluereg);
687 if (!bpp16)
688 {
689 if (dpi == 1200)
690 write_regs (udev, 16, 0x9b, 0x00, 0x98, 0xc7, 0x99, 0x99, 0x9a, 0xd5,
691 0x9b, 0x01, 0x98, 0x00, 0x99, 0x00, 0x9a, 0x00, 0x9b,
692 0x02, 0x98, 0xc8, 0x99, 0x99, 0x9a, 0xd3, 0x9b, 0x03,
693 0x98, 0x00, 0x99, 0x00, 0x9a, 0x00);
694 else if (dpi == 150)
695 write_regs (udev, 16, 0x9b, 0x00, 0x98, 0x94, 0x99, 0x67, 0x9a, 0x83,
696 0x9b, 0x01, 0x98, 0x00, 0x99, 0x00, 0x9a, 0x00, 0x9b,
697 0x02, 0x98, 0x7e, 0x99, 0x5d, 0x9a, 0x7d, 0x9b, 0x03,
698 0x98, 0x00, 0x99, 0x00, 0x9a, 0x00);
699 else
700 write_regs (udev, 16, 0x9b, 0x00, 0x98, 0xb3, 0x99, 0x72, 0x9a, 0x9d,
701 0x9b, 0x01, 0x98, 0x00, 0x99, 0x00, 0x9a, 0x00, 0x9b,
702 0x02, 0x98, 0xa3, 0x99, 0x6f, 0x9a, 0x94, 0x9b, 0x03,
703 0x98, 0x00, 0x99, 0x00, 0x9a, 0x00);
704 }
705 else
706 {
707 if (dpi == 1200)
708 write_regs (udev, 16, 0x9b, 0x00, 0x98, 0xb9, 0x99, 0x7a, 0x9a, 0xd6,
709 0x9b, 0x01, 0x98, 0x00, 0x99, 0x00, 0x9a, 0x00, 0x9b,
710 0x02, 0x98, 0xbc, 0x99, 0x7c, 0x9a, 0xd3, 0x9b, 0x03,
711 0x98, 0x00, 0x99, 0x00, 0x9a, 0x00);
712 else if (dpi == 150)
713 write_regs (udev, 16, 0x9b, 0x00, 0x98, 0x9c, 0x99, 0x5f, 0x9a, 0x87,
714 0x9b, 0x01, 0x98, 0x00, 0x99, 0x00, 0x9a, 0x00, 0x9b,
715 0x02, 0x98, 0x97, 0x99, 0x58, 0x9a, 0x81, 0x9b, 0x03,
716 0x98, 0x00, 0x99, 0x00, 0x9a, 0x00);
717 else
718 write_regs (udev, 16, 0x9b, 0x00, 0x98, 0x9d, 0x99, 0x79, 0x9a, 0x8e,
719 0x9b, 0x01, 0x98, 0x00, 0x99, 0x00, 0x9a, 0x00, 0x9b,
720 0x02, 0x98, 0x89, 0x99, 0x71, 0x9a, 0x80, 0x9b, 0x03,
721 0x98, 0x00, 0x99, 0x00, 0x9a, 0x00);
722 }
723 write_regs (udev, 4, 0x83, 0xa2, 0x85, 0x98, 0x83, 0x82, 0x85, 0x3a);
724 write_regs (udev, 1, 0x9d, 0x80);
725 write_regs (udev, 1, 0x9d, 0x00);
726 if (!bpp16)
727 {
728 if (dpi == 1200)
729 write_regs (udev, 1, 0x94, 0x51);
730 else
731 write_regs (udev, 1, 0x94, 0x41);
732 }
733 else
734 {
735 if (dpi == 1200)
736 write_regs (udev, 1, 0x94, 0x71);
737 else
738 write_regs (udev, 1, 0x94, 0x61);
739 }
740 lightmap = (unsigned short *) malloc (whitemapsize);
741 calc_lightmap (whitescan, lightmap, 0, dpi, gain, offset);
742 select_pixels (lightmap, dpi, leftpix, scanpix);
743 if (dpi == 1200)
744 write_regs (udev, 6, 0xb0, 0x00, 0xb1, 0x80, 0xb2, 0x06, 0xb3, 0xff, 0xb4,
745 0xff, 0xb5, 0x06);
746 else
747 write_regs (udev, 6, 0xb0, 0x00, 0xb1, 0x40, 0xb2, 0x07, 0xb3, 0xff, 0xb4,
748 0x7f, 0xb5, 0x07);
749 write_vctl (udev, 0x0c, 0x0002, whitemapsize, 0x00);
750 usb_bulk_write (udev, 2, (unsigned char *) lightmap, whitemapsize,
751 wr_timeout);
752
753 calc_lightmap (whitescan, lightmap, 1, dpi, gain, offset);
754 if (dpi == 1200)
755 write_regs (udev, 6, 0xb0, 0x00, 0xb1, 0x00, 0xb2, 0x07, 0xb3, 0xff, 0xb4,
756 0x7f, 0xb5, 0x07);
757 else
758 write_regs (udev, 6, 0xb0, 0x00, 0xb1, 0x80, 0xb2, 0x07, 0xb3, 0xff, 0xb4,
759 0xbf, 0xb5, 0x07);
760 write_vctl (udev, 0x0c, 0x0002, whitemapsize, 0x00);
761 fix_endian_short (&GRAYMASK, 1);
762 if (gray)
763 for (i = 0; i < whitemapsize / 2; i++)
764 lightmap[i] |= GRAYMASK;
765 usb_bulk_write (udev, 2, (unsigned char *) lightmap, whitemapsize,
766 wr_timeout);
767
768 calc_lightmap (whitescan, lightmap, 2, dpi, gain, offset);
769 if (dpi == 1200)
770 write_regs (udev, 6, 0xb0, 0x00, 0xb1, 0x80, 0xb2, 0x07, 0xb3, 0xff, 0xb4,
771 0xff, 0xb5, 0x07);
772 else
773 write_regs (udev, 6, 0xb0, 0x00, 0xb1, 0xc0, 0xb2, 0x07, 0xb3, 0xff, 0xb4,
774 0xff, 0xb5, 0x07);
775 write_vctl (udev, 0x0c, 0x0002, whitemapsize, 0x00);
776 usb_bulk_write (udev, 2, (unsigned char *) lightmap, whitemapsize,
777 wr_timeout);
778
779 free (whitescan);
780 free (lightmap);
781
782 if (!bpp16)
783 download_lut8 (udev, dpi, gray ? 0 : 1);
784
785 write_regs (udev, 4, 0x83, 0xa2, 0x85, 0x01, 0x83, 0x82, 0x85, 0x00);
786 write_regs (udev, 1, 0x9d, 0x80);
787 write_regs (udev, 1, 0x9d, 0x00);
788
789 if (!bpp16)
790 {
791 if (dpi == 1200)
792 write_regs (udev, 10, 0xb0, 0x00, 0xb1, 0x00, 0xb2, 0x00, 0xb3, 0xff,
793 0xb4, 0x1f, 0xb5, 0x06, 0xb6, 0x01, 0xb7, 0x00, 0xb8,
794 0x43, 0xb9, 0x2d);
795 else if (dpi == 150)
796 write_regs (udev, 10, 0xb0, 0x00, 0xb1, 0x00, 0xb2, 0x00, 0xb3, 0xff,
797 0xb4, 0x0f, 0xb5, 0x07, 0xb6, 0x01, 0xb7, 0x00, 0xb8,
798 0xe0, 0xb9, 0x37);
799 else
800 write_regs (udev, 10, 0xb0, 0x00, 0xb1, 0x00, 0xb2, 0x00, 0xb3, 0xff,
801 0xb4, 0x0f, 0xb5, 0x07, 0xb6, 0x01, 0xb7, 0x00, 0xb8,
802 0x90, 0xb9, 0x37);
803 }
804 else
805 {
806 if (dpi == 1200)
807 write_regs (udev, 10, 0xb0, 0x00, 0xb1, 0x00, 0xb2, 0x00, 0xb3, 0xff,
808 0xb4, 0xff, 0xb5, 0x03, 0xb6, 0x01, 0xb7, 0x00, 0xb8,
809 0x87, 0xb9, 0x18);
810 else if (dpi == 150)
811 write_regs (udev, 10, 0xb0, 0x00, 0xb1, 0x00, 0xb2, 0x00, 0xb3, 0xff,
812 0xb4, 0xff, 0xb5, 0x03, 0xb6, 0x01, 0xb7, 0x00, 0xb8,
813 0xc1, 0xb9, 0x1e);
814 else
815 write_regs (udev, 10, 0xb0, 0x00, 0xb1, 0x00, 0xb2, 0x00, 0xb3, 0xff,
816 0xb4, 0xff, 0xb5, 0x03, 0xb6, 0x01, 0xb7, 0x00, 0xb8,
817 0x21, 0xb9, 0x1e);
818 }
819
820 /* [86,89] controls number of 300dpi steps to scan */
821 botreg = scanlines * (1200 / dpi) + 400;
822 write_regs (udev, 6, 0xc0, 0x00, 0x84, 0x00, 0x84, 0xb4, 0x80, 0xe1, 0xcf,
823 0x04, 0x82, 0x00);
824
825 if (!bpp16)
826 {
827 if (dpi == 300)
828 write_regs (udev, 18, 0x83, 0xa2, 0x85, 0x04, 0x83, 0x82, 0x85, 0x00,
829 0xbc, 0x20, 0xbd, 0x10, 0x88, 0xd0, 0xc1, 0x01, 0xc2,
830 0x00, 0xc3, 0x04, 0xc4, 0x20, 0xc5, 0x10, 0xc6, 0xc3,
831 0xc7, 0xd0, 0xc8, 0x12, 0xc0, 0xd1, 0x89, botreg & 255,
832 0x86, 255 & (botreg >> 8));
833 else if (dpi == 600)
834 write_regs (udev, 18, 0x83, 0xa2, 0x85, 0x04, 0x83, 0x82, 0x85, 0x00,
835 0xbc, 0x20, 0xbd, 0x10, 0x88, 0xd0, 0xc1, 0x01, 0xc2,
836 0x00, 0xc3, 0x04, 0xc4, 0x20, 0xc5, 0x10, 0xc6, 0xc3,
837 0xc7, 0xd0, 0xc8, 0x16, 0xc0, 0xd1, 0x89, botreg & 255,
838 0x86, 255 & (botreg >> 8));
839 else if (dpi == 1200)
840 write_regs (udev, 18, 0x83, 0xa2, 0x85, 0x02, 0x83, 0x82, 0x85, 0x00,
841 0xbc, 0x20, 0xbd, 0x08, 0x88, 0xa4, 0xc1, 0x02, 0xc2,
842 0x00, 0xc3, 0x02, 0xc4, 0x20, 0xc5, 0x08, 0xc6, 0x96,
843 0xc7, 0xa4, 0xc8, 0x06, 0xc0, 0xd2, 0x89, botreg & 255,
844 0x86, 255 & (botreg >> 8));
845 else if (dpi == 150)
846 write_regs (udev, 18, 0x83, 0xa2, 0x85, 0x06, 0x83, 0x82, 0x85, 0x00,
847 0xbc, 0x1c, 0xbd, 0x08, 0x88, 0xe0, 0xc1, 0x01, 0xc2,
848 0x00, 0xc3, 0x03, 0xc4, 0x1c, 0xc5, 0x08, 0xc6, 0xd7,
849 0xc7, 0xe0, 0xc8, 0x11, 0xc0, 0xd1, 0x89, botreg & 255,
850 0x86, 255 & (botreg >> 8));
851
852 if (dpi == 300)
853 write_regs (udev, 8, 0xbb, 0x01, 0x9b, 0x24, 0x8b, 0x00, 0x8e, 0x80,
854 0xbf, 0x00, 0x90, 0x20, 0x91, 0x00, 0x83, 0x82);
855 else if (dpi == 600)
856 write_regs (udev, 8, 0xbb, 0x02, 0x9b, 0x24, 0x8b, 0x00, 0x8e, 0x80,
857 0xbf, 0x00, 0x90, 0x20, 0x91, 0x00, 0x83, 0x82);
858 else if (dpi == 1200)
859 write_regs (udev, 8, 0xbb, 0x02, 0x9b, 0x24, 0x8b, 0x00, 0x8e, 0x80,
860 0xbf, 0x00, 0x90, 0x20, 0x91, 0x00, 0x83, 0x82);
861 else if (dpi == 150)
862 write_regs (udev, 8, 0xbb, 0x00, 0x9b, 0x24, 0x8b, 0x00, 0x8e, 0x80,
863 0xbf, 0x00, 0x90, 0x20, 0x91, 0x00, 0x83, 0x82);
864 }
865 else
866 {
867 if (dpi == 300)
868 write_regs (udev, 18, 0x83, 0xa2, 0x85, 0x04, 0x83, 0x82, 0x85, 0x00,
869 0xbc, 0x20, 0xbd, 0x10, 0x88, 0xd0, 0xc1, 0x01, 0xc2,
870 0x00, 0xc3, 0x04, 0xc4, 0x20, 0xc5, 0x10, 0xc6, 0xc3,
871 0xc7, 0xd0, 0xc8, 0x13, 0xc0, 0xd1, 0x89, botreg & 255,
872 0x86, 255 & (botreg >> 8));
873 else if (dpi == 150)
874 write_regs (udev, 18, 0x83, 0xa2, 0x85, 0x06, 0x83, 0x82, 0x85, 0x00,
875 0xbc, 0x1c, 0xbd, 0x08, 0x88, 0xe0, 0xc1, 0x01, 0xc2,
876 0x00, 0xc3, 0x03, 0xc4, 0x1c, 0xc5, 0x08, 0xc6, 0xd7,
877 0xc7, 0xe0, 0xc8, 0x12, 0xc0, 0xd1, 0x89, botreg & 255,
878 0x86, 255 & (botreg >> 8));
879 else if (dpi == 1200)
880 write_regs (udev, 18, 0x83, 0xa2, 0x85, 0x02, 0x83, 0x82, 0x85, 0x00,
881 0xbc, 0x20, 0xbd, 0x08, 0x88, 0xa4, 0xc1, 0x02, 0xc2,
882 0x00, 0xc3, 0x02, 0xc4, 0x20, 0xc5, 0x08, 0xc6, 0x96,
883 0xc7, 0xa4, 0xc8, 0x0c, 0xc0, 0xd2, 0x89, botreg & 255,
884 0x86, 255 & (botreg >> 8));
885 else if (dpi == 600)
886 write_regs (udev, 18, 0x83, 0xa2, 0x85, 0x04, 0x83, 0x82, 0x85, 0x00,
887 0xbc, 0x20, 0xbd, 0x10, 0x88, 0xd0, 0xc1, 0x01, 0xc2,
888 0x00, 0xc3, 0x04, 0xc4, 0x20, 0xc5, 0x10, 0xc6, 0xc3,
889 0xc7, 0xd0, 0xc8, 0x1a, 0xc0, 0xd1, 0x89, botreg & 255,
890 0x86, 255 & (botreg >> 8));
891
892 if (dpi == 300)
893 write_regs (udev, 8, 0xbb, 0x02, 0x9b, 0x24, 0x8b, 0x00, 0x8e, 0x80,
894 0xbf, 0x00, 0x90, 0x70, 0x91, 0x00, 0x83, 0x82);
895 else if (dpi == 150)
896 write_regs (udev, 8, 0xbb, 0x01, 0x9b, 0x24, 0x8b, 0x00, 0x8e, 0x80,
897 0xbf, 0x00, 0x90, 0x70, 0x91, 0x00, 0x83, 0x82);
898 else if (dpi == 1200)
899 write_regs (udev, 8, 0xbb, 0x05, 0x9b, 0x24, 0x8b, 0x00, 0x8e, 0x80,
900 0xbf, 0x00, 0x90, 0x70, 0x91, 0x00, 0x83, 0x82);
901 else if (dpi == 600)
902 write_regs (udev, 8, 0xbb, 0x04, 0x9b, 0x24, 0x8b, 0x00, 0x8e, 0x80,
903 0xbf, 0x00, 0x90, 0x70, 0x91, 0x00, 0x83, 0x82);
904
905
906 }
907
908 if (gray)
909 write_regs (udev, 1, 0xbe, 0x05);
910 else
911 write_regs (udev, 1, 0xbe, 0x0d);
912 write_vctl (udev, 0x0c, 0x0003, 0x0001, 0x00);
913 usb_bulk_read (udev, 1, &rd_byte, 1, rd_timeout);
914 write_vctl (udev, 0x0c, 0x0001, 0x0000, 0x00);
915
916 #ifndef BACKENDNAME
917 sprintf (fname, "%d.%s", dpi, gray ? "pgm" : "ppm");
918 if (stname)
919 strcpy (fname, stname);
920 sprintf (head, "P%d\n%d %d\n%d\n", gray ? 5 : 6, scanpix, scanlines,
921 bpp16 ? 65535 : 255);
922 if (nohead)
923 head[0] = 0;
924 if (!raw)
925 record_image (udev, fname, dpi, scanpix, scanlines, gray, head, bpp16);
926 else
927 record_head (udev, fname,
928 scanpix * (gray ? 1 : 3) * (bpp16 ? 2 : 1) * scanlines, "");
929
930 reset_scanner (udev);
931 idle_ab (udev);
932 set_lamp_timer (udev, 5);
933 #endif
934 }
935