• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /* sane - Scanner Access Now Easy.
2 
3    pieusb.c
4 
5    Copyright (C) 2012-2015 Jan Vleeshouwers, Michael Rickmann, Klaus Kaempf
6 
7    This file is part of the SANE package.
8 
9    This program is free software; you can redistribute it and/or
10    modify it under the terms of the GNU General Public License as
11    published by the Free Software Foundation; either version 2 of the
12    License, or (at your option) any later version.
13 
14    This program is distributed in the hope that it will be useful, but
15    WITHOUT ANY WARRANTY; without even the implied warranty of
16    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
17    General Public License for more details.
18 
19    You should have received a copy of the GNU General Public License
20    along with this program.  If not, see <https://www.gnu.org/licenses/>.
21 
22    As a special exception, the authors of SANE give permission for
23    additional uses of the libraries contained in this release of SANE.
24 
25    The exception is that, if you link a SANE library with other files
26    to produce an executable, this does not by itself cause the
27    resulting executable to be covered by the GNU General Public
28    License.  Your use of that executable is in no way restricted on
29    account of linking the SANE library code into it.
30 
31    This exception does not, however, invalidate any other reasons why
32    the executable file might be covered by the GNU General Public
33    License.
34 
35    If you submit changes to SANE to the maintainers to be included in
36    a subsequent release, you agree by submitting the changes that
37    those changes may be distributed with this exception intact.
38 
39    If you write modifications of your own for SANE, it is your choice
40    whether to permit this exception to apply to your modifications.
41    If you do not wish that, delete this exception notice.  */
42 
43 /* =========================================================================
44  *
45  * SANE interface to three Reflecta USB scanners with USB-id 0x05e3/0x0145:
46  * - Reflecta CrystalScan 7200 (model id 0x30)
47  * - Reflecta ProScan 7200 (model id 0x36)
48  * - Reflecta 6000 Multiple Slide Scanner (model id 0x3A)
49  *
50  * ========================================================================= */
51 
52 #define DEBUG_NOT_STATIC
53 /* --------------------------------------------------------------------------
54  *
55  * INCLUDES
56  *
57  * --------------------------------------------------------------------------*/
58 
59 #include "../include/sane/config.h"
60 /* Standard includes for various utiliy functions */
61 #include <stdio.h> /* for FILE */
62 #include <string.h> /* for strlen */
63 #include <stdlib.h> /* for NULL */
64 #include <stdint.h>
65 #include <math.h>
66 
67 /* Configuration defines */
68 #include "../include/sane/config.h"
69 
70 /* SANE includes */
71 #include "../include/sane/sane.h"
72 #include "../include/sane/saneopts.h"
73 #include "../include/sane/sanei_usb.h"
74 #include "../include/sane/sanei_config.h"
75 
76 /* Backend includes */
77 #define BACKEND_NAME pieusb
78 #include "../include/sane/sanei_backend.h"
79 #include "pieusb.h"
80 #include "pieusb_specific.h"
81 
82 #define CAN_DO_4_CHANNEL_TIFF
83 
84 #ifdef CAN_DO_4_CHANNEL_TIFF
85 extern void write_tiff_rgbi_header (FILE *fptr, int width, int height, int depth, int resolution, const char *icc_profile);
86 #endif
87 
88 /* --------------------------------------------------------------------------
89  *
90  * DEFINES
91  *
92  * --------------------------------------------------------------------------*/
93 
94 /* Build number of this backend */
95 #define BUILD 1
96 
97 /* Configuration filename */
98 #define PIEUSB_CONFIG_FILE "pieusb.conf"
99 
100 /* Debug error levels */
101 #define DBG_error        1      /* errors */
102 #define DBG_warning      3      /* warnings */
103 #define DBG_info         5      /* information */
104 #define DBG_info_sane    7      /* information sane interface level */
105 #define DBG_inquiry      8      /* inquiry data */
106 #define DBG_info_proc    9      /* information pieusb backend functions */
107 #define DBG_info_scan   11      /* information scanner commands */
108 #define DBG_info_usb    13      /* information usb level functions */
109 
110 /* device flags */
111 
112 #define FLAG_SLIDE_TRANSPORT 0x01
113 /* Some scanners do understand SLIDE_TRANSPORT but not CMD_17 - introducing a new flag */
114 #define FLAG_CMD_17_NOSUPPORT 0x02
115 
116 /* --------------------------------------------------------------------------
117  *
118  * SUPPORTED DEVICES SPECIFICS
119  *
120  * --------------------------------------------------------------------------*/
121 
122 struct Pieusb_USB_Device_Entry* pieusb_supported_usb_device_list = NULL;
123 struct Pieusb_USB_Device_Entry pieusb_supported_usb_device; /* for searching */
124 
125 /* --------------------------------------------------------------------------
126  *
127  * LISTS OF ACTIVE DEVICE DEFINITIONS AND SCANNERS
128  *
129  * --------------------------------------------------------------------------*/
130 
131 Pieusb_Device_Definition *pieusb_definition_list_head = NULL;
132 static Pieusb_Scanner *first_handle = NULL;
133 static const SANE_Device **devlist = NULL;
134 
135 /* --------------------------------------------------------------------------
136  *
137  * SANE INTERFACE
138  *
139  * --------------------------------------------------------------------------*/
140 
141 /**
142  * Initializes the debugging system, the USB system, the version code and
143  * 'attaches' available scanners, i.e. creates device definitions for all
144  * scanner devices found.
145  *
146  * @param version_code
147  * @param authorize
148  * @return SANE_STATUS_GOOD
149  */
150 SANE_Status
sane_init(SANE_Int * version_code,SANE_Auth_Callback __sane_unused__ authorize)151 sane_init (SANE_Int * version_code, SANE_Auth_Callback __sane_unused__ authorize)
152 {
153     FILE *fp;
154     char config_line[PATH_MAX];
155     SANE_Word vendor_id;
156     SANE_Word product_id;
157     SANE_Int model_number;
158     SANE_Int flags;
159     SANE_Status status;
160     int i;
161 
162     /* Initialize debug logging */
163     DBG_INIT ();
164 
165     DBG (DBG_info_sane, "sane_init() build %d\n", BUILD);
166 
167     /* Set version code to current major, minor and build number */
168     if (version_code)
169         *version_code = SANE_VERSION_CODE (SANE_CURRENT_MAJOR, SANE_CURRENT_MINOR, BUILD);
170 
171     /* Initialize usb */
172     sanei_usb_init ();
173     sanei_usb_set_timeout (30 * 1000); /* 30 sec timeout */
174 
175     /* There are currently 3 scanners hardcoded into this backend, see below.
176      * The config file may add other scanners using a line like
177      * usb 0x1234 0x5678 0x9A
178      * where the first two hex numbers are vendor and product id, and the last
179      * number is the model number. Unfortunately, this is not according to the
180      * config file standard. Anyone any suggestions? */
181 
182     /* Create default list */
183     pieusb_supported_usb_device_list = calloc (4, sizeof(struct Pieusb_USB_Device_Entry));
184     if (pieusb_supported_usb_device_list == NULL)
185       return SANE_STATUS_NO_MEM;
186     /* Reflecta CrystalScan 7200, model number 0x30 */
187     pieusb_supported_usb_device_list[0].vendor = 0x05e3;
188     pieusb_supported_usb_device_list[0].product = 0x0145;
189     pieusb_supported_usb_device_list[0].model = 0x30;
190     pieusb_supported_usb_device_list[0].flags = 0;
191     /* Reflecta ProScan 7200, model number 0x36 */
192     pieusb_supported_usb_device_list[1].vendor = 0x05e3;
193     pieusb_supported_usb_device_list[1].product = 0x0145;
194     pieusb_supported_usb_device_list[1].model = 0x36;
195     pieusb_supported_usb_device_list[1].flags = 0;
196     /* Reflecta 6000 Multiple Slide Scanner, model number 0x3a */
197     pieusb_supported_usb_device_list[2].vendor = 0x05e3;
198     pieusb_supported_usb_device_list[2].product = 0x0142;
199     pieusb_supported_usb_device_list[2].model = 0x3a;
200     pieusb_supported_usb_device_list[2].flags = FLAG_SLIDE_TRANSPORT;
201     /* end of list */
202     pieusb_supported_usb_device_list[3].vendor = 0;
203     pieusb_supported_usb_device_list[3].product = 0;
204     pieusb_supported_usb_device_list[3].model = 0;
205     pieusb_supported_usb_device_list[3].flags = 0;
206 
207     /* Add entries from config file */
208     fp = sanei_config_open (PIEUSB_CONFIG_FILE);
209     if (!fp) {
210         DBG (DBG_info_sane, "sane_init() did not find a config file, using default list of supported devices\n");
211     } else {
212         while (sanei_config_read (config_line, sizeof (config_line), fp)) {
213             /* Ignore line comments and empty lines */
214             if (config_line[0] == '#') continue;
215             if (strlen (config_line) == 0) continue;
216             /* Ignore lines which do not begin with 'usb ' */
217             if (strncmp (config_line, "usb ", 4) != 0) continue;
218             /* Parse vendor-id, product-id and model number and add to list */
219             DBG (DBG_info_sane, "sane_init() config file parsing %s\n", config_line);
220             status = sanei_pieusb_parse_config_line(config_line, &vendor_id, &product_id, &model_number, &flags);
221             if (status == SANE_STATUS_GOOD) {
222                 DBG (DBG_info_sane, "sane_init() config file lists device %04x %04x %02x %02x\n",vendor_id, product_id, model_number, flags);
223                 if (!sanei_pieusb_supported_device_list_contains(vendor_id, product_id, model_number, flags)) {
224                     DBG (DBG_info_sane, "sane_init() adding device %04x %04x %02x %02x\n",vendor_id, product_id, model_number, flags);
225                     sanei_pieusb_supported_device_list_add(vendor_id, product_id, model_number, flags);
226                 } else {
227                     DBG (DBG_info_sane, "sane_init() list already contains %04x %04x %02x %02x\n", vendor_id, product_id, model_number, flags);
228                 }
229             } else {
230                 DBG (DBG_info_sane, "sane_init() config file parsing %s: error\n", config_line);
231             }
232 	}
233         fclose (fp);
234     }
235 
236     /* Loop through supported device list */
237     i = 0;
238     while (pieusb_supported_usb_device_list[i].vendor != 0) {
239         /* Check if the supported device is present. If so, create a device
240          * definition structure for it.
241          * The variable pieusb_supported_usb_device is set to current values,
242          * which are used in the callback. */
243         pieusb_supported_usb_device.vendor = pieusb_supported_usb_device_list[i].vendor;
244         pieusb_supported_usb_device.product = pieusb_supported_usb_device_list[i].product;
245         pieusb_supported_usb_device.model = pieusb_supported_usb_device_list[i].model;
246         pieusb_supported_usb_device.flags = pieusb_supported_usb_device_list[i].flags;
247         pieusb_supported_usb_device.device_number = -1; /* No device number (yet) */
248         DBG( DBG_info_sane, "sane_init() looking for scanner %04x %04x model %02x, flags %02x\n",
249              pieusb_supported_usb_device.vendor,
250              pieusb_supported_usb_device.product,
251              pieusb_supported_usb_device.model,
252              pieusb_supported_usb_device.flags);
253         sanei_usb_find_devices (pieusb_supported_usb_device.vendor, pieusb_supported_usb_device.product, sanei_pieusb_find_device_callback);
254         i++;
255     }
256     return SANE_STATUS_GOOD;
257 }
258 
259 /**
260  * Backend exit.
261  * Clean up allocated memory.
262  */
263 void
sane_exit(void)264 sane_exit (void)
265 {
266     Pieusb_Device_Definition *dev, *next;
267 
268     DBG (DBG_info_sane, "sane_exit()\n");
269 
270     for (dev = pieusb_definition_list_head; dev; dev = next) {
271         next = dev->next;
272         free((void *)dev->sane.name);
273         free((void *)dev->sane.vendor);
274         free((void *)dev->sane.model);
275         free (dev->version);
276         free (dev);
277     }
278     pieusb_definition_list_head = NULL;
279 
280     if (devlist) {
281         free (devlist);
282         devlist = NULL;
283     }
284 }
285 
286 /**
287  * Create a SANE device list from the device list generated by sane_init().
288  *
289  * @param device_list List of SANE_Device elements
290  * @param local_only If true, disregard network scanners. Not applicable for USB scanners.
291  * @return SANE_STATUS_GOOD, or SANE_STATUS_NO_MEM if the list cannot be allocated
292  */
293 SANE_Status
sane_get_devices(const SANE_Device *** device_list,SANE_Bool __sane_unused__ local_only)294 sane_get_devices (const SANE_Device *** device_list, SANE_Bool __sane_unused__ local_only)
295 {
296     Pieusb_Device_Definition *dev;
297     int i;
298 
299     DBG (DBG_info_sane, "sane_get_devices\n");
300 
301     /* Create SANE_DEVICE list from device list created in sane_init() */
302     i = 0;
303     for (dev = pieusb_definition_list_head; dev; dev = dev->next) {
304         i++;
305     }
306     if (devlist) {
307         free (devlist);
308     }
309     devlist = malloc ((i + 1) * sizeof (devlist[0]));
310     if (!devlist) {
311         return SANE_STATUS_NO_MEM;
312     }
313     i = 0;
314     for (dev = pieusb_definition_list_head; dev; dev = dev->next) {
315         devlist[i++] = &dev->sane;
316     }
317     devlist[i] = NULL;
318     *device_list = devlist;
319     return SANE_STATUS_GOOD;
320 }
321 
322 /**
323  * Open the scanner with the given devicename and return a handle to it, which
324  * is a pointer to a Pieusb_Scanner struct. The handle will be an input to
325  * a couple of other functions of the SANE interface.
326  *
327  * @param devicename Name of the device, corresponds to SANE_Device.name
328  * @param handle handle to scanner (pointer to a Pieusb_Scanner struct)
329  * @return SANE_STATUS_GOOD if the device has been opened
330  */
331 SANE_Status
sane_open(SANE_String_Const devicename,SANE_Handle * handle)332 sane_open (SANE_String_Const devicename, SANE_Handle * handle)
333 {
334     Pieusb_Device_Definition *dev;
335     SANE_Status status;
336     Pieusb_Scanner *scanner, *s;
337 
338     DBG (DBG_info_sane, "sane_open(%s)\n", devicename);
339 
340     /* Search for devicename */
341     if (devicename[0]) {
342         for (dev = pieusb_definition_list_head; dev; dev = dev->next) {
343 	  if (strcmp (dev->sane.name, devicename) == 0) {
344 	      break;
345 	  }
346         }
347         if (!dev) {
348             /* Is it a valid USB device? */
349             SANE_Word vendor;
350             SANE_Word product;
351             int i = 0;
352 
353             status = sanei_usb_get_vendor_product_byname (devicename, &vendor, &product);
354             if (status != SANE_STATUS_GOOD) {
355                 DBG (DBG_error, "sane_open: sanei_usb_get_vendor_product_byname failed %s\n", devicename);
356                 return status;
357             }
358             /* Get vendor-product-model & verify that is is supported */
359             /* Loop through supported device list */
360             while (pieusb_supported_usb_device_list[i].vendor != 0) {
361                 /* Check if vendor and product match */
362                 if (pieusb_supported_usb_device_list[i].vendor == vendor
363                         && pieusb_supported_usb_device_list[i].product == product) {
364                     /* Check if a supported device is present
365                      * If so, create a device definition structure for it. */
366                     /* Set pieusb_supported_usb_device to current values: these are used in callback */
367                     pieusb_supported_usb_device.vendor = vendor;
368                     pieusb_supported_usb_device.product = product;
369                     pieusb_supported_usb_device.model = pieusb_supported_usb_device_list[i].model;
370                     pieusb_supported_usb_device.flags = pieusb_supported_usb_device_list[i].flags;
371                     pieusb_supported_usb_device.device_number = -1;
372                     sanei_usb_find_devices (vendor, product, sanei_pieusb_find_device_callback);
373                     if (pieusb_supported_usb_device.device_number == -1) {
374                         /* Did not succeed in opening the USB device, which is an error.
375                          * This error is not caught by sanei_usb_find_devices(), so handle
376                          * it here. */
377                         DBG (DBG_error, "sane_open: sanei_usb_find_devices did not open device %s\n", devicename);
378                         return SANE_STATUS_INVAL;
379                     }
380                 }
381                 i++;
382             }
383             /* Now rescan the device list to see if it is present */
384             for (dev = pieusb_definition_list_head; dev; dev = dev->next) {
385               if (strcmp (dev->sane.name, devicename) == 0) {
386                   break;
387               }
388             }
389 	}
390     } else {
391         /* empty devicename -> use first device */
392         dev = pieusb_definition_list_head;
393     }
394     /* If no device found, return error */
395     if (!dev) {
396         return SANE_STATUS_INVAL;
397     }
398 
399     /* Now create a scanner structure to return */
400 
401     /* Check if we are not opening the same scanner again. */
402     for (s = first_handle; s; s = s->next) {
403         if (s->device->sane.name == devicename) {
404             *handle = s;
405             return SANE_STATUS_GOOD;
406         }
407     }
408 
409     /* Create a new scanner instance */
410     scanner = malloc (sizeof (*scanner));
411     if (!scanner) {
412         return SANE_STATUS_NO_MEM;
413     }
414     memset (scanner, 0, sizeof (*scanner));
415     scanner->device = dev;
416     sanei_usb_open (dev->sane.name, &scanner->device_number);
417     scanner->cancel_request = 0;
418     scanner->shading_data_present = SANE_FALSE;
419     /* Options and buffers */
420     (void)sanei_pieusb_init_options (scanner);
421 
422     /* wait for warmup */
423     status = sanei_pieusb_wait_ready (scanner, 0);
424     if (status != SANE_STATUS_GOOD) {
425       sanei_usb_close(scanner->device_number);
426       free (scanner);
427       DBG (DBG_error, "sane_open: scanner not ready\n");
428       return status;
429     }
430 
431     /* First time settings */
432     /* ? */
433     /* Insert newly opened handle into list of open handles: */
434     scanner->next = first_handle;
435     first_handle = scanner;
436 
437     *handle = scanner;
438     return SANE_STATUS_GOOD;
439 }
440 
441 /**
442  * Close the scanner and remove the scanner from the list of active scanners.
443  *
444  * @param handle Scanner handle
445  */
446 void
sane_close(SANE_Handle handle)447 sane_close (SANE_Handle handle)
448 {
449     Pieusb_Scanner *prev, *scanner;
450     SANE_Int k;
451 
452     DBG (DBG_info_sane, "sane_close()\n");
453 
454     /* Find handle in list of open handles: */
455     prev = 0;
456     for (scanner = first_handle; scanner; scanner = scanner->next)  {
457         if (scanner == handle) {
458             break;
459         }
460         prev = scanner;
461     }
462     /* Not a handle we know about. This may happen since all different backend
463      * scanner instances are all cast to SANE_Handle (a void pointer) */
464     if (!scanner) {
465         DBG (DBG_error, "sane_close(): invalid handle %p\n", handle);
466         return;
467     }
468 
469     /* Stop scan if still scanning */
470     if (scanner->scanning) {
471         sanei_pieusb_on_cancel(scanner);
472     }
473 
474     /* USB scanners may be still open here */
475     if (scanner->device_number >= 0) {
476         sanei_usb_reset (scanner->device_number);
477         sanei_usb_close (scanner->device_number);
478     }
479     /* Remove handle from list */
480     if (prev) {
481         prev->next = scanner->next;
482     } else {
483         first_handle = scanner->next;
484     }
485 
486     /* Free scanner related allocated memory and the scanner itself */
487     /*TODO: check if complete */
488     if (scanner->buffer.data) sanei_pieusb_buffer_delete(&scanner->buffer);
489     free (scanner->ccd_mask);
490     for (k=0; k<4; k++) free (scanner->shading_ref[k]);
491     free (scanner->val[OPT_MODE].s);
492     free (scanner->val[OPT_HALFTONE_PATTERN].s);
493     free (scanner);
494 }
495 
496 /**
497  * Get option descriptor. Return the option descriptor with the given index
498  *
499  * @param handle Scanner handle
500  * @param option Index of option descriptor to return
501  * @return The option descriptor
502  */
503 const SANE_Option_Descriptor *
sane_get_option_descriptor(SANE_Handle handle,SANE_Int option)504 sane_get_option_descriptor (SANE_Handle handle, SANE_Int option)
505 {
506     Pieusb_Scanner *scanner = handle;
507 
508     DBG (DBG_info_proc, "sane_get_option_descriptor() option=%d\n", option);
509 
510     if ((unsigned) option >= NUM_OPTIONS)
511     {
512       return 0;
513     }
514 
515     return scanner->opt + option;
516 }
517 
518 /**
519  * Set or inquire the current value of option number 'option' of the device
520  * represented by the given handle.
521  *
522  * @param handle Scanner handle
523  * @param option Index of option to set or get
524  * @param action Determines if the option value is read or set
525  * @param val Pointer to value to set or get
526  * @param info About set result. May be NULL.
527  * @return SANE_STATUS_GOOD, or SANE_STATUS_INVAL if a parameter cannot be set
528  */
529 SANE_Status
sane_control_option(SANE_Handle handle,SANE_Int option,SANE_Action action,void * val,SANE_Int * info)530 sane_control_option (SANE_Handle handle, SANE_Int option, SANE_Action action,
531 		     void *val, SANE_Int * info)
532 {
533     Pieusb_Scanner *scanner = handle;
534     SANE_Status status;
535     SANE_Word cap;
536     SANE_String_Const name;
537 
538     DBG(DBG_info_sane,"sane_control_option()\n");
539     if (info) {
540         *info = 0;
541     }
542 
543     /* Don't set or get options while the scanner is busy */
544     if (scanner->scanning) {
545         DBG(DBG_error,"Device busy scanning, no option returned\n");
546         return SANE_STATUS_DEVICE_BUSY;
547     }
548 
549     /* Check if option index is between bounds */
550     if ((unsigned) option >= NUM_OPTIONS) {
551         DBG(DBG_error,"Index too large, no option returned\n");
552         return SANE_STATUS_INVAL;
553     }
554 
555     /* Check if option is switched on */
556     cap = scanner->opt[option].cap;
557     if (!SANE_OPTION_IS_ACTIVE (cap))
558     {
559         DBG(DBG_error,"Option inactive (%s)\n", scanner->opt[option].name);
560         return SANE_STATUS_INVAL;
561     }
562 
563     /* Get name of option */
564     name = scanner->opt[option].name;
565     if (!name)
566     {
567       name = "(no name)";
568     }
569 
570     /* */
571     switch (action) {
572         case SANE_ACTION_GET_VALUE:
573 
574             DBG (DBG_info_sane, "get %s [#%d]\n", name, option);
575 
576             switch (option) {
577 
578                 /* word options: */
579                 case OPT_NUM_OPTS:
580                 case OPT_BIT_DEPTH:
581                 case OPT_RESOLUTION:
582                 case OPT_TL_X:
583                 case OPT_TL_Y:
584                 case OPT_BR_X:
585                 case OPT_BR_Y:
586                 case OPT_THRESHOLD:
587                 case OPT_SHARPEN:
588                 case OPT_SHADING_ANALYSIS:
589                 case OPT_FAST_INFRARED:
590 	        case OPT_ADVANCE_SLIDE:
591                 case OPT_CORRECT_SHADING:
592                 case OPT_CORRECT_INFRARED:
593                 case OPT_CLEAN_IMAGE:
594                 case OPT_SMOOTH_IMAGE:
595                 case OPT_TRANSFORM_TO_SRGB:
596                 case OPT_INVERT_IMAGE:
597                 case OPT_PREVIEW:
598                 case OPT_SAVE_SHADINGDATA:
599                 case OPT_SAVE_CCDMASK:
600 	        case OPT_LIGHT:
601 	        case OPT_DOUBLE_TIMES:
602                 case OPT_SET_EXPOSURE_R:
603                 case OPT_SET_EXPOSURE_G:
604                 case OPT_SET_EXPOSURE_B:
605                 case OPT_SET_EXPOSURE_I:
606                 case OPT_SET_GAIN_R:
607                 case OPT_SET_GAIN_G:
608                 case OPT_SET_GAIN_B:
609                 case OPT_SET_GAIN_I:
610                 case OPT_SET_OFFSET_R:
611                 case OPT_SET_OFFSET_G:
612                 case OPT_SET_OFFSET_B:
613                 case OPT_SET_OFFSET_I:
614                     *(SANE_Word *) val = scanner->val[option].w;
615                     DBG (DBG_info_sane, "get %s [#%d] val=%d\n", name, option,scanner->val[option].w);
616                     return SANE_STATUS_GOOD;
617 
618                 /* word-array options: => for exposure gain offset? */
619                 case OPT_CROP_IMAGE:
620                     memcpy (val, scanner->val[option].wa, scanner->opt[option].size);
621                     return SANE_STATUS_GOOD;
622 
623                 /* string options */
624                 case OPT_MODE:
625                 case OPT_CALIBRATION_MODE:
626                 case OPT_GAIN_ADJUST:
627                 case OPT_HALFTONE_PATTERN:
628                     strcpy (val, scanner->val[option].s);
629                     DBG (DBG_info_sane, "get %s [#%d] val=%s\n", name, option,scanner->val[option].s);
630                     return SANE_STATUS_GOOD;
631             }
632             break;
633 
634         case SANE_ACTION_SET_VALUE:
635 
636             switch (scanner->opt[option].type) {
637                 case SANE_TYPE_INT:
638                     DBG (DBG_info_sane, "set %s [#%d] to %d, size=%d\n", name, option, *(SANE_Word *) val, scanner->opt[option].size);
639                     break;
640                 case SANE_TYPE_FIXED:
641                     DBG (DBG_info_sane, "set %s [#%d] to %f\n", name, option, SANE_UNFIX (*(SANE_Word *) val));
642                     break;
643                 case SANE_TYPE_STRING:
644                     DBG (DBG_info_sane, "set %s [#%d] to %s\n", name, option, (char *) val);
645                     break;
646                 case SANE_TYPE_BOOL:
647                     DBG (DBG_info_sane, "set %s [#%d] to %d\n", name, option, *(SANE_Word *) val);
648                     break;
649                 default:
650                     DBG (DBG_info_sane, "set %s [#%d]\n", name, option);
651             }
652             /* Check if option can be set */
653             if (!SANE_OPTION_IS_SETTABLE (cap)) {
654               return SANE_STATUS_INVAL;
655             }
656             /* Check if new value within bounds */
657             status = sanei_constrain_value (scanner->opt + option, val, info);
658             if (status != SANE_STATUS_GOOD) {
659               return status;
660             }
661             /* Set option and handle info return */
662             switch (option)
663             {
664                 /* (mostly) side-effect-free word options: */
665                 case OPT_BIT_DEPTH:
666                 case OPT_RESOLUTION:
667                 case OPT_TL_X:
668                 case OPT_TL_Y:
669                 case OPT_BR_X:
670                 case OPT_BR_Y:
671                 case OPT_SHARPEN:
672                 case OPT_SHADING_ANALYSIS:
673                 case OPT_FAST_INFRARED:
674                     if (info) {
675                         *info |= SANE_INFO_RELOAD_PARAMS;
676                     }
677                   /* fall through */
678                 case OPT_NUM_OPTS:
679                 case OPT_PREVIEW:
680 	        case OPT_ADVANCE_SLIDE:
681                 case OPT_CORRECT_SHADING:
682                 case OPT_CORRECT_INFRARED:
683                 case OPT_CLEAN_IMAGE:
684                 case OPT_SMOOTH_IMAGE:
685                 case OPT_TRANSFORM_TO_SRGB:
686                 case OPT_INVERT_IMAGE:
687                 case OPT_SAVE_SHADINGDATA:
688                 case OPT_SAVE_CCDMASK:
689                 case OPT_THRESHOLD:
690 	        case OPT_LIGHT:
691 	        case OPT_DOUBLE_TIMES:
692                 case OPT_SET_GAIN_R:
693                 case OPT_SET_GAIN_G:
694                 case OPT_SET_GAIN_B:
695                 case OPT_SET_GAIN_I:
696                 case OPT_SET_OFFSET_R:
697                 case OPT_SET_OFFSET_G:
698                 case OPT_SET_OFFSET_B:
699                 case OPT_SET_OFFSET_I:
700                 case OPT_SET_EXPOSURE_R:
701                 case OPT_SET_EXPOSURE_G:
702                 case OPT_SET_EXPOSURE_B:
703                 case OPT_SET_EXPOSURE_I:
704                     scanner->val[option].w = *(SANE_Word *) val;
705                     break;
706 
707                 /* side-effect-free word-array options: */
708                 case OPT_CROP_IMAGE:
709                     memcpy (scanner->val[option].wa, val, scanner->opt[option].size);
710                     break;
711 
712                 /* options with side-effects: */
713                 case OPT_MODE:
714                 {
715                     /* Free current setting */
716                     if (scanner->val[option].s) {
717                         free (scanner->val[option].s);
718                     }
719                     /* New setting */
720                     scanner->val[option].s = (SANE_Char *) strdup (val);
721                     /* Info */
722                     if (info) {
723                         *info |= SANE_INFO_RELOAD_OPTIONS | SANE_INFO_RELOAD_PARAMS;
724                     }
725                     break;
726                 }
727 
728                 case OPT_CALIBRATION_MODE:
729                 case OPT_GAIN_ADJUST:
730                 case OPT_HALFTONE_PATTERN:
731                 {
732                      /* Free current setting */
733                     if (scanner->val[option].s) {
734                         free (scanner->val[option].s);
735                     }
736                     /* New setting */
737                     scanner->val[option].s = (SANE_Char *) strdup (val);
738                     break;
739                 }
740 
741             }
742 
743             /* Check the whole set */
744             if (sanei_pieusb_analyse_options(scanner)) {
745                 return SANE_STATUS_GOOD;
746             } else {
747                 return SANE_STATUS_INVAL;
748             }
749 
750             break;
751         default:
752             return SANE_STATUS_INVAL;
753             break;
754     }
755     return SANE_STATUS_INVAL;
756 }
757 
758 /**
759  * Obtain the current scan parameters. The returned parameters are guaranteed
760  * to be accurate between the time a scan has been started (sane start() has
761  * been called) and the completion of that request. Outside of that window, the
762  * returned values are best-effort estimates of what the parameters will be when
763  * sane start() gets invoked. - says the SANE standard.
764  *
765  * @param handle Scanner handle
766  * @param params Scan parameters
767  * @return SANE_STATUS_GOOD
768  */
769 SANE_Status
sane_get_parameters(SANE_Handle handle,SANE_Parameters * params)770 sane_get_parameters (SANE_Handle handle, SANE_Parameters * params)
771 {
772     Pieusb_Scanner *scanner = handle;
773     const char *mode;
774     double resolution, width, height;
775     SANE_Int colors;
776 
777     DBG (DBG_info_sane, "sane_get_parameters\n");
778 
779     if (params) {
780 
781         if (scanner->scanning) {
782             /* sane_start() initialized a SANE_Parameters struct in the scanner */
783             DBG (DBG_info_sane, "sane_get_parameters from scanner values\n");
784             params->bytes_per_line = scanner->scan_parameters.bytes_per_line;
785             params->depth = scanner->scan_parameters.depth;
786             params->format = scanner->scan_parameters.format;
787             params->last_frame = scanner->scan_parameters.last_frame;
788             params->lines = scanner->scan_parameters.lines;
789             params->pixels_per_line = scanner->scan_parameters.pixels_per_line;
790         } else {
791             /* Calculate appropriate values from option settings */
792             DBG (DBG_info_sane, "sane_get_parameters from option values\n");
793             if (scanner->val[OPT_PREVIEW].b) {
794                 resolution = scanner->device->fast_preview_resolution;
795             } else {
796                 resolution = SANE_UNFIX(scanner->val[OPT_RESOLUTION].w);
797             }
798             DBG (DBG_info_sane, "  resolution %f\n", resolution);
799             width = SANE_UNFIX(scanner->val[OPT_BR_X].w)-SANE_UNFIX(scanner->val[OPT_TL_X].w);
800             height = SANE_UNFIX(scanner->val[OPT_BR_Y].w)-SANE_UNFIX(scanner->val[OPT_TL_Y].w);
801             DBG (DBG_info_sane, "  width x height: %f x %f\n", width, height);
802             params->lines = height / MM_PER_INCH * resolution;
803             params->pixels_per_line = width / MM_PER_INCH * resolution;
804             mode = scanner->val[OPT_MODE].s;
805             if (strcmp(mode, SANE_VALUE_SCAN_MODE_LINEART) == 0) {
806                 params->format = SANE_FRAME_GRAY;
807                 params->depth = 1;
808                 colors = 1;
809             } else if(strcmp(mode, SANE_VALUE_SCAN_MODE_HALFTONE) == 0) {
810                 params->format = SANE_FRAME_GRAY;
811                 params->depth = 1;
812                 colors = 1;
813             } else if(strcmp(mode, SANE_VALUE_SCAN_MODE_GRAY) == 0) {
814                 params->format = SANE_FRAME_GRAY;
815                 params->depth = scanner->val[OPT_BIT_DEPTH].w;
816                 colors = 1;
817             } else if(strcmp(mode, SANE_VALUE_SCAN_MODE_RGBI) == 0) {
818                 params->format = SANE_FRAME_RGB; /* was: SANE_FRAME_RGBI */
819                 params->depth = scanner->val[OPT_BIT_DEPTH].w;
820                 colors = 4;
821             } else { /* SANE_VALUE_SCAN_MODE_COLOR */
822                 params->format = SANE_FRAME_RGB;
823                 params->depth = scanner->val[OPT_BIT_DEPTH].w;
824                 colors = 3;
825             }
826             DBG (DBG_info_sane, "  colors: %d\n", colors);
827             if (params->depth == 1) {
828                 params->bytes_per_line = colors * (params->pixels_per_line + 7)/8;
829             } else if (params->depth <= 8) {
830                 params->bytes_per_line = colors * params->pixels_per_line;
831             } else if (params->depth <= 16) {
832                 params->bytes_per_line = 2 * colors * params->pixels_per_line;
833             }
834             params->last_frame = SANE_TRUE;
835         }
836 
837         DBG(DBG_info_sane,"sane_get_parameters(): SANE parameters\n");
838         DBG(DBG_info_sane," format = %d\n",params->format);
839         DBG(DBG_info_sane," last_frame = %d\n",params->last_frame);
840         DBG(DBG_info_sane," bytes_per_line = %d\n",params->bytes_per_line);
841         DBG(DBG_info_sane," pixels_per_line = %d\n",params->pixels_per_line);
842         DBG(DBG_info_sane," lines = %d\n",params->lines);
843         DBG(DBG_info_sane," depth = %d\n",params->depth);
844 
845     } else {
846 
847         DBG(DBG_info_sane," no params argument, no values returned\n");
848 
849     }
850 
851     return SANE_STATUS_GOOD;
852 }
853 
854 /**
855  * Initiates acquisition of an image from the scanner.
856  * SCAN Phase 1: initialization and calibration
857  * (SCAN Phase 2: line-by-line scan & read is not implemented)
858  * SCAN Phase 3: get CCD-mask
859  * SCAN phase 4: scan slide and save data in scanner buffer
860 
861  * @param handle Scanner handle
862  * @return
863  */
864 SANE_Status
sane_start(SANE_Handle handle)865 sane_start (SANE_Handle handle)
866 {
867     struct Pieusb_Scanner *scanner = handle;
868     struct Pieusb_Command_Status status;
869     SANE_Byte colors;
870     const char *mode;
871     SANE_Bool shading_correction_relevant;
872     SANE_Bool infrared_post_processing_relevant;
873     SANE_Status st;
874     SANE_Int bytes_per_line;
875 
876     SANE_Int shading_width;
877     SANE_Int shading_idx;
878 
879     struct Pieusb_Exposure_Time exptime = {
880       0x93, /* code 0x93 */
881       3 * 2 * sizeof(SANE_Int), /* number of bytes in rest of structure */
882       { { 0x02, 100 }, { 0x04, 100 }, { 0x08, 100 } }
883     };
884 
885     struct Pieusb_Highlight_Shadow shadow = {
886       0x94, /* code 0x94 */
887       3 * 2 * sizeof(SANE_Int), /* number of bytes in rest of structure */
888       { { 0x02, 100 }, { 0x04, 100 }, { 0x08, 100 } }
889     };
890 
891     DBG (DBG_info_sane, "sane_start()\n");
892 
893     /* ----------------------------------------------------------------------
894      *
895      * Exit if currently scanning
896      *
897      * ---------------------------------------------------------------------- */
898     if (scanner->scanning) {
899         DBG (DBG_error, "sane_start(): scanner is already scanning, exiting\n");
900         return SANE_STATUS_DEVICE_BUSY;
901     }
902 
903     /* ----------------------------------------------------------------------
904      *
905      * Exit with pause if not warmed up
906      *
907      * ---------------------------------------------------------------------- */
908 
909     sanei_pieusb_cmd_read_state (scanner->device_number, &(scanner->state), &status);
910     if (status.pieusb_status != PIEUSB_STATUS_GOOD) {
911         if (status.pieusb_status == PIEUSB_STATUS_DEVICE_BUSY)
912 	  return SANE_STATUS_DEVICE_BUSY; /* was: SANE_STATUS_WARMING_UP */
913         DBG (DBG_error, "sane_start(): warmed up check returns status: %s\n",  sane_strstatus (sanei_pieusb_convert_status(status.pieusb_status)));
914         return SANE_STATUS_IO_ERROR;
915     }
916     if (scanner->state.warmingUp) {
917         DBG (DBG_error, "sane_start(): warming up, exiting\n");
918         /* Seen SANE_STATUS_WARMING_UP in scanimage => enabled */
919         sleep (10); /* scanimage does not pause, so do it here */
920         return SANE_STATUS_DEVICE_BUSY; /* was: SANE_STATUS_WARMING_UP */
921     }
922 
923     /* ----------------------------------------------------------------------
924      * set exposure time
925      * ---------------------------------------------------------------------- */
926 
927     sanei_pieusb_cmd_set_exposure_time (scanner->device_number, &exptime, &status);
928     if (status.pieusb_status != PIEUSB_STATUS_GOOD) {
929       DBG (DBG_error, "sane_start(): sanei_pieusb_cmd_set_exposure_time failed: %d\n", status.pieusb_status);
930       return SANE_STATUS_IO_ERROR;
931     }
932 
933     /* ----------------------------------------------------------------------
934      * set highlight shadow
935      * ---------------------------------------------------------------------- */
936 
937     sanei_pieusb_cmd_set_highlight_shadow (scanner->device_number, &shadow, &status);
938     if (status.pieusb_status != PIEUSB_STATUS_GOOD) {
939       DBG (DBG_error, "sane_start(): sanei_pieusb_cmd_set_highlight_shadow failed: %d\n", status.pieusb_status);
940       return SANE_STATUS_IO_ERROR;
941     }
942 
943     /* ----------------------------------------------------------------------
944      * get calibration info
945      * ---------------------------------------------------------------------- */
946 
947     sanei_pieusb_cmd_get_shading_parms (scanner->device_number, scanner->device->shading_parameters, &status);
948     if (status.pieusb_status != PIEUSB_STATUS_GOOD) {
949       DBG (DBG_error, "sane_scan: sanei_pieusb_cmd_get_shading_parms failed: %d\n", status.pieusb_status);
950       return SANE_STATUS_INVAL;
951     }
952     shading_width = scanner->device->shading_parameters[0].pixelsPerLine;
953     DBG (DBG_info, "shading_width %d\n", shading_width);
954     for (shading_idx = 0; shading_idx < SHADING_PARAMETERS_INFO_COUNT; shading_idx++) {
955       scanner->shading_ref[shading_idx] =
956         realloc(scanner->shading_ref[shading_idx], 2 * shading_width * sizeof(SANE_Int));
957       if (scanner->shading_ref[shading_idx] == NULL) {
958         return SANE_STATUS_NO_MEM;
959       }
960     }
961     scanner->ccd_mask = realloc (scanner->ccd_mask, shading_width);
962     scanner->ccd_mask_size = shading_width;
963     if (scanner->ccd_mask == NULL) {
964       return SANE_STATUS_NO_MEM;
965     }
966 
967     /* ----------------------------------------------------------------------
968      *
969      * Standard run does;
970      * - set exposure time 0x0A/0x13
971      * - set highlight shadow 0x0A/0x14
972      * - read shading parameters 0x0A/0x95/0x08
973      * - set scan frame 0x0A/0x12
974      *   "12 00 0a00 80 00 0300 0000 b829 e31a"
975      *    => 0:12 1:0 2:10 4:80 5:0 6:3 8:0 10:10680 12:6883
976      * - read gain offset 0xD7
977      * - set gain offset 0xDC
978      * - set mode 0x15
979      *   "00 0f   2c01 80   04  04  00 01    0a     00 00 00  80  10 00"
980      *       size res  pass dpt frm    ord   bitmap       ptn thr
981      *       15   300  RGB  8   inx    intel 1=sharpen    0   128
982      *                                       3=skipshad
983      *
984      * ---------------------------------------------------------------------- */
985 
986     /* ----------------------------------------------------------------------
987      *
988      * Show and check options
989      *
990      * ---------------------------------------------------------------------- */
991     sanei_pieusb_print_options (scanner);
992     if (!sanei_pieusb_analyse_options (scanner)) {
993         return SANE_STATUS_IO_ERROR;
994     }
995 
996     /* ----------------------------------------------------------------------
997      *
998      * Set scan frame
999      *
1000      * ---------------------------------------------------------------------- */
1001     if (sanei_pieusb_set_frame_from_options (scanner) != SANE_STATUS_GOOD) {
1002         return SANE_STATUS_IO_ERROR;
1003     }
1004 
1005     /* ----------------------------------------------------------------------
1006      *
1007      * Function 17
1008      * This function is not supported by all scanners which are capable of
1009      *  slide transport, therefore FLAG_CMD_17_NOSUPPORT was introduced.
1010      *
1011      * ---------------------------------------------------------------------- */
1012 
1013     if ( (scanner->device->flags & FLAG_SLIDE_TRANSPORT) & !(scanner->device->flags & FLAG_CMD_17_NOSUPPORT) )     {
1014         sanei_pieusb_cmd_17 (scanner->device_number, 1, &status);
1015         if (status.pieusb_status != PIEUSB_STATUS_GOOD) {
1016           DBG (DBG_error, "sane_start(): sanei_pieusb_cmd_17 failed: %d\n", status.pieusb_status);
1017           return SANE_STATUS_IO_ERROR;
1018         }
1019         st = sanei_pieusb_wait_ready (scanner, 0);
1020         if (st != SANE_STATUS_GOOD) {
1021           DBG (DBG_error, "sane_start(): scanner not ready after sanei_pieusb_cmd_17: %d\n", st);
1022           return st;
1023         }
1024     }
1025     /* ----------------------------------------------------------------------
1026      *
1027      * Get & set initial gains and offsets
1028      *
1029      * There does not seem to be much reason to set exposure/gain/offset
1030      * now, but it does make a large difference in speed, because it
1031      * creates a small BADF-table. This is probably because without SET GAIN
1032      * OFFSET, extraEntries has a random value (it is not initialised).
1033      *
1034      * TODO: test if this may be done just once, in sane_open().
1035      *
1036      * ---------------------------------------------------------------------- */
1037 
1038     if (sanei_pieusb_set_gain_offset (scanner, scanner->val[OPT_CALIBRATION_MODE].s) != SANE_STATUS_GOOD) {
1039         return SANE_STATUS_IO_ERROR;
1040     }
1041 
1042     st = sanei_pieusb_wait_ready (scanner, 0);
1043     if (st != SANE_STATUS_GOOD) {
1044       DBG (DBG_error, "sane_start: scanner not ready %d\n", st);
1045       return st;
1046     }
1047 
1048     /* ----------------------------------------------------------------------
1049      *
1050      * Set mode
1051      *
1052      * ---------------------------------------------------------------------- */
1053     if (sanei_pieusb_set_mode_from_options (scanner) != SANE_STATUS_GOOD) {
1054         return SANE_STATUS_IO_ERROR;
1055     }
1056 
1057     /* ----------------------------------------------------------------------
1058      *
1059      * Init slide transport
1060      *
1061      * ---------------------------------------------------------------------- */
1062     if (scanner->device->flags & FLAG_SLIDE_TRANSPORT) {
1063         sanei_pieusb_cmd_slide (scanner->device_number, SLIDE_INIT, &status);
1064         if (status.pieusb_status != PIEUSB_STATUS_GOOD) {
1065           DBG (DBG_error, "sane_start(): sanei_pieusb_cmd_slide failed: %d\n", status.pieusb_status);
1066           return SANE_STATUS_IO_ERROR;
1067         }
1068         st = sanei_pieusb_wait_ready (scanner, 0);
1069         if (st != SANE_STATUS_GOOD) {
1070           DBG (DBG_error, "sane_start: scanner not ready %d\n", st);
1071           return st;
1072         }
1073     }
1074     /* Enter SCAN phase 1 */
1075     DBG (DBG_info_sane, "sane_start(): scan phase 1\n");
1076 
1077     /* ----------------------------------------------------------------------
1078      *
1079      * Start scan & wait until device ready
1080      *
1081      * ---------------------------------------------------------------------- */
1082     scanner->scanning = SANE_TRUE;
1083     scanner->cancel_request = SANE_FALSE;
1084     for (;;) {
1085       sanei_pieusb_cmd_start_scan (scanner->device_number, &status);
1086       if (status.pieusb_status != PIEUSB_STATUS_WARMING_UP)
1087 	break;
1088       sleep(5);
1089     }
1090     sanei_pieusb_wait_ready (scanner, 0);
1091     if ((status.pieusb_status == PIEUSB_STATUS_MUST_CALIBRATE)
1092         || (scanner->val[OPT_SHADING_ANALYSIS].b != 0)) {
1093 
1094         /* Overriding skip calibration */
1095         DBG (DBG_info_sane, "sane_start(): process shading data\n");
1096 
1097         /* ------------------------------------------------------------------
1098          *
1099          * Get and set gain and offset
1100          * Get settings from scanner, from preview data, from options,
1101          * or use defaults.
1102          *
1103          * ------------------------------------------------------------------ */
1104         if (sanei_pieusb_set_gain_offset (scanner, scanner->val[OPT_CALIBRATION_MODE].s) != SANE_STATUS_GOOD) {
1105             sanei_pieusb_cmd_stop_scan (scanner->device_number, &status);
1106             scanner->scanning = SANE_FALSE;
1107             return SANE_STATUS_IO_ERROR;
1108         }
1109         /* ------------------------------------------------------------------
1110          *
1111          * Obtain shading data
1112          * Get parameters from scanner->device->shading_parameters[0] although
1113          * it's 45 lines, scanner->ccd_mask_size pixels, 16 bit depth in all cases.
1114          *
1115          * ------------------------------------------------------------------ */
1116         if (sanei_pieusb_get_shading_data (scanner) != SANE_STATUS_GOOD) {
1117             sanei_pieusb_cmd_stop_scan (scanner->device_number, &status);
1118             scanner->scanning = SANE_FALSE;
1119             return SANE_STATUS_IO_ERROR;
1120         }
1121     }
1122 
1123     /* Enter SCAN phase 2 */
1124     DBG (DBG_info_sane, "sane_start(): scan phase 2\n");
1125 
1126     /* SCAN phase 2 (line-by-line scan) not implemented */
1127 
1128     st = sanei_pieusb_wait_ready (scanner, 0);
1129     if (st != SANE_STATUS_GOOD) {
1130       DBG (DBG_error, "sane_start: scanner not ready %d\n", st);
1131       return st;
1132     }
1133 
1134     /* Enter SCAN phase 3 */
1135 
1136     DBG (DBG_info_sane, "sane_start(): scan phase 3\n");
1137 
1138     /* Handle cancel request */
1139     if (scanner->cancel_request) {
1140         return sanei_pieusb_on_cancel (scanner);
1141     }
1142 
1143     /* ----------------------------------------------------------------------
1144      *
1145      * Get CCD mask
1146      *
1147      * ---------------------------------------------------------------------- */
1148 
1149     if (sanei_pieusb_get_ccd_mask (scanner) != SANE_STATUS_GOOD) {
1150         sanei_pieusb_cmd_stop_scan (scanner->device_number, &status);
1151         scanner->scanning = SANE_FALSE;
1152         return SANE_STATUS_IO_ERROR;
1153     }
1154 
1155     /* Enter SCAN phase 4 */
1156 
1157     /* ----------------------------------------------------------------------
1158      *
1159      * Read scan parameters & wait until ready for reading
1160      *
1161      * ---------------------------------------------------------------------- */
1162     if (sanei_pieusb_get_parameters (scanner, &bytes_per_line) != SANE_STATUS_GOOD) {
1163         sanei_pieusb_cmd_stop_scan (scanner->device_number, &status);
1164         scanner->scanning = SANE_FALSE;
1165         return SANE_STATUS_IO_ERROR;
1166     }
1167 
1168     st = sanei_pieusb_wait_ready (scanner, 0);
1169     if (st != SANE_STATUS_GOOD) {
1170       DBG (DBG_error, "sane_start: scanner not ready %d\n", st);
1171       return st;
1172     }
1173 
1174     /* ----------------------------------------------------------------------
1175      *
1176      * Prepare read buffer
1177      * Currently this buffer is always a memory mapped buffer
1178      * Might be faster to use RAM buffers for small images (such as preview)
1179      *
1180      * ---------------------------------------------------------------------- */
1181     colors = 0x00;
1182     switch (scanner->mode.passes) {
1183         case SCAN_FILTER_RED: colors = 0x01; break;
1184         case SCAN_FILTER_GREEN: colors = 0x02; break;
1185         case SCAN_FILTER_BLUE: colors = 0x04; break;
1186         case SCAN_FILTER_INFRARED: colors = 0x08; break;
1187         case SCAN_ONE_PASS_COLOR: colors = 0x07; break;
1188         case SCAN_ONE_PASS_RGBI: colors = 0x0F; break;
1189     }
1190     if (scanner->buffer.data) sanei_pieusb_buffer_delete(&scanner->buffer); /* free resources from previous invocation */
1191     st = sanei_pieusb_buffer_create (&(scanner->buffer), scanner->scan_parameters.pixels_per_line,
1192 			       scanner->scan_parameters.lines, colors,
1193 			       scanner->scan_parameters.depth);
1194     if (st != SANE_STATUS_GOOD) {
1195         scanner->scanning = SANE_FALSE;
1196         return st;
1197     }
1198 
1199     /* ----------------------------------------------------------------------
1200      *
1201      * Read all image data into the buffer
1202      *
1203      * ---------------------------------------------------------------------- */
1204     if (sanei_pieusb_get_scan_data (scanner, bytes_per_line) != SANE_STATUS_GOOD) {
1205         scanner->scanning = SANE_FALSE;
1206         return SANE_STATUS_IO_ERROR;
1207     }
1208     sleep(2);
1209     st = sanei_pieusb_wait_ready (scanner, 0);
1210     if (st != SANE_STATUS_GOOD) {
1211       DBG (DBG_error, "sane_start(): scanner not ready after sanei_pieusb_get_scan_data: %d\n", st);
1212       scanner->scanning = SANE_FALSE;
1213       return st;
1214     }
1215 
1216     /* ----------------------------------------------------------------------
1217      *
1218      * Advance to next slide (except for preview)
1219      *
1220      * ---------------------------------------------------------------------- */
1221 
1222     if (scanner->device->flags & FLAG_SLIDE_TRANSPORT) {
1223         if (scanner->val[OPT_ADVANCE_SLIDE].b && !scanner->val[OPT_PREVIEW].b) {
1224             sanei_pieusb_cmd_slide (scanner->device_number, SLIDE_NEXT, &status);
1225             if (status.pieusb_status != PIEUSB_STATUS_GOOD) {
1226                 DBG (DBG_error, "sane_start(): sanei_pieusb_cmd_slide failed: %d\n", status.pieusb_status);
1227             }
1228         }
1229     }
1230 
1231     /* ----------------------------------------------------------------------
1232      *
1233      * Post processing:
1234      * 1. Correct for shading
1235      * 2. Remove R-component from IR data
1236      * 3. Remove dust
1237      *
1238      * ---------------------------------------------------------------------- */
1239 
1240     mode = scanner->val[OPT_MODE].s;
1241     if (strcmp(mode, SANE_VALUE_SCAN_MODE_LINEART) == 0) {
1242         shading_correction_relevant = SANE_FALSE; /* Shading correction irrelavant at bit depth 1 */
1243         infrared_post_processing_relevant = SANE_FALSE; /* No infrared, no postprocessing */
1244     } else if (strcmp(mode, SANE_VALUE_SCAN_MODE_HALFTONE) == 0) {
1245         shading_correction_relevant = SANE_FALSE; /* Shading correction irrelavant at bit depth 1 */
1246         infrared_post_processing_relevant = SANE_FALSE; /* No infrared, no postprocessing */
1247     } else if (strcmp(mode, SANE_VALUE_SCAN_MODE_GRAY) == 0) {
1248         shading_correction_relevant = SANE_TRUE;
1249         infrared_post_processing_relevant = SANE_FALSE; /* No infrared, no postprocessing */
1250     } else if (scanner->val[OPT_PREVIEW].b) {
1251         /* Catch preview here, otherwise next ifs get complicated */
1252         shading_correction_relevant = SANE_TRUE;
1253         infrared_post_processing_relevant = SANE_FALSE;
1254     } else if (strcmp(mode, SANE_VALUE_SCAN_MODE_RGBI) == 0) {
1255         shading_correction_relevant = SANE_TRUE;
1256         infrared_post_processing_relevant = SANE_TRUE;
1257     } else if (strcmp(mode, SANE_VALUE_SCAN_MODE_COLOR) == 0 && scanner->val[OPT_CLEAN_IMAGE].b) {
1258         shading_correction_relevant = SANE_TRUE;
1259         infrared_post_processing_relevant = SANE_TRUE;
1260     } else { /* SANE_VALUE_SCAN_MODE_COLOR */
1261         shading_correction_relevant = SANE_TRUE;
1262         infrared_post_processing_relevant = SANE_TRUE;
1263     }
1264     if (scanner->val[OPT_CORRECT_SHADING].b && shading_correction_relevant) {
1265         if (scanner->shading_data_present) {
1266             sanei_pieusb_correct_shading (scanner, &scanner->buffer);
1267         } else {
1268             DBG(DBG_warning, "sane_start(): unable to correct for shading, no shading data available\n");
1269         }
1270     }
1271     if ((scanner->val[OPT_CORRECT_INFRARED].b || scanner->val[OPT_CLEAN_IMAGE].b) && !scanner->val[OPT_PREVIEW].b && infrared_post_processing_relevant) {
1272         /* Create array of pointers to color planes R, G, B, I */
1273         SANE_Uint *planes[PLANES];
1274         SANE_Int N;
1275         N = scanner->buffer.width * scanner->buffer.height;
1276         planes[0] = scanner->buffer.data;
1277         planes[1] = scanner->buffer.data + N;
1278         planes[2] = scanner->buffer.data + 2 * N;
1279         planes[3] = scanner->buffer.data + 3 * N;
1280         sanei_ir_init ();
1281         sanei_pieusb_post (scanner, planes, scanner->buffer.colors);
1282     }
1283 
1284     /* Save preview data. Preview data only used once to set gain and offset. */
1285     if (scanner->val[OPT_PREVIEW].b) {
1286         sanei_pieusb_analyze_preview(scanner);
1287     } else {
1288         scanner->preview_done = SANE_FALSE;
1289     }
1290 
1291     /* Modify buffer in case the buffer has infrared, but no infrared should be returned */
1292     if (scanner->buffer.colors == PLANES && (strcmp(mode,SANE_VALUE_SCAN_MODE_COLOR) == 0 && scanner->val[OPT_CLEAN_IMAGE].b)) {
1293         DBG(DBG_info_sane, "sane_start(): modifying buffer to ignore I\n");
1294         /* Base buffer parameters */
1295         scanner->buffer.colors = 3;
1296         /* Derived quantities */
1297         scanner->buffer.image_size_bytes = scanner->buffer.colors * scanner->buffer.height * scanner->buffer.line_size_bytes;
1298         scanner->buffer.color_index_infrared = -1;
1299         scanner->buffer.bytes_unread = scanner->buffer.bytes_unread * 3 / 4;
1300         scanner->buffer.bytes_written = scanner->buffer.bytes_written * 3 / 4;
1301     }
1302 
1303     return SANE_STATUS_GOOD;
1304 
1305 }
1306 
1307 /**
1308  * Read image data from the scanner buffer.
1309  *
1310  * @param handle
1311  * @param buf
1312  * @param max_len
1313  * @param len
1314  * @return
1315  */
1316 SANE_Status
sane_read(SANE_Handle handle,SANE_Byte * buf,SANE_Int max_len,SANE_Int * len)1317 sane_read (SANE_Handle handle, SANE_Byte * buf, SANE_Int max_len, SANE_Int * len)
1318 {
1319 
1320     struct Pieusb_Scanner *scanner = handle;
1321     SANE_Int return_size;
1322 
1323     DBG(DBG_info_sane, "sane_read(): requested %d bytes\n", max_len);
1324 
1325     /* No reading if not scanning */
1326     if (!scanner->scanning) {
1327         *len = 0;
1328         return SANE_STATUS_IO_ERROR; /* SANE standard does not allow a SANE_STATUS_INVAL return */
1329     }
1330 
1331     /* Handle cancel request */
1332     if (scanner->cancel_request) {
1333         return sanei_pieusb_on_cancel(scanner);
1334     }
1335 #if 0
1336     /* Return image data, just read from scanner buffer */
1337     DBG(DBG_info_sane, "sane_read():\n");
1338     DBG(DBG_info_sane, "  image size %d\n", scanner->buffer.image_size_bytes);
1339     DBG(DBG_info_sane, "  unread     %d\n", scanner->buffer.bytes_unread);
1340     DBG(DBG_info_sane, "  read       %d\n", scanner->buffer.bytes_read);
1341     DBG(DBG_info_sane, "  max_len    %d\n", max_len);
1342 #endif
1343     if (scanner->buffer.bytes_read > scanner->buffer.image_size_bytes) {
1344         /* Test if not reading past buffer boundaries */
1345         DBG(DBG_error, "sane_read(): reading past buffer boundaries (contains %d, read %d)\n", scanner->buffer.image_size_bytes, scanner->buffer.bytes_read);
1346         *len = 0;
1347         sanei_pieusb_on_cancel(scanner);
1348         return SANE_STATUS_EOF;
1349     } else if (scanner->buffer.bytes_read == scanner->buffer.image_size_bytes) {
1350         /* Return EOF since all data of this frame has already been read. */
1351         *len = 0;
1352         scanner->scanning = SANE_FALSE;
1353         return SANE_STATUS_EOF;
1354     } else if (scanner->buffer.bytes_unread >= max_len) {
1355         /* Already enough data to return, do not read */
1356         DBG(DBG_info_sane, "sane_read(): buffer suffices (contains %d, requested %d)\n", scanner->buffer.bytes_unread, max_len);
1357         return_size = max_len;
1358     } else if (scanner->buffer.bytes_read + scanner->buffer.bytes_unread == scanner->buffer.image_size_bytes) {
1359         /* All the remaining data is in the buffer, do not read */
1360         DBG(DBG_info_sane, "sane_read(): buffer suffices (contains %d, requested %d, last batch though)\n", scanner->buffer.bytes_unread, max_len);
1361         return_size = scanner->buffer.bytes_unread;
1362     } else {
1363         /* Should not happen in this implementation - all data read by sane_start() */
1364         DBG(DBG_error, "sane_read(): shouldn't be here...\n");
1365         return SANE_STATUS_IO_ERROR;
1366     }
1367 
1368     /* Check */
1369     if (return_size == 0 && scanner->buffer.bytes_read < scanner->buffer.image_size_bytes) {
1370         DBG(DBG_error, "sane_read(): unable to service read request, %d bytes in frame, %d read\n", scanner->buffer.image_size_bytes, scanner->buffer.bytes_read);
1371     }
1372 
1373     /* Return the available data: Output return_size bytes from buffer */
1374     sanei_pieusb_buffer_get(&scanner->buffer, buf, max_len, len);
1375 #if 0
1376     DBG(DBG_info_sane, "sane_read(): currently read %.2f lines of %d\n",
1377       (double)scanner->buffer.bytes_written/(scanner->buffer.line_size_bytes*scanner->buffer.colors),
1378       scanner->buffer.height);
1379     DBG(DBG_info_sane, "sane_read(): returning %d bytes (requested %d), returned %d of %d \n",
1380       *len, max_len,scanner->buffer.bytes_read, scanner->buffer.image_size_bytes);
1381 #endif
1382     return SANE_STATUS_GOOD;
1383 
1384 }
1385 
1386 /**
1387  * Request cancellation of current scanning process.
1388  *
1389  * @param handle Scanner handle
1390  */
1391 void
sane_cancel(SANE_Handle handle)1392 sane_cancel (SANE_Handle handle)
1393 {
1394     struct Pieusb_Scanner *scanner = handle;
1395 
1396     DBG (DBG_info_sane, "sane_cancel\n");
1397 
1398     if (scanner->scanning) {
1399         scanner->cancel_request = 1;
1400     }
1401 }
1402 
1403 /**
1404  * Set the I/O mode of handle h. The I/O mode can be either blocking or
1405  * non-blocking, but for USB devices, only blocking mode is supported.
1406  *
1407  * @param handle Scanner handle
1408  * @param non_blocking
1409  * @return SANE_STATUS_UNSUPPORTED;
1410  */
1411 SANE_Status
sane_set_io_mode(SANE_Handle handle,SANE_Bool non_blocking)1412 sane_set_io_mode (SANE_Handle handle, SANE_Bool non_blocking)
1413 {
1414     /* Pieusb_Scanner *scanner = handle; */
1415 
1416     DBG (DBG_info_sane, "sane_set_io_mode: handle = %p, non_blocking = %s\n", handle, non_blocking == SANE_TRUE ? "true" : "false");
1417 
1418     if (non_blocking) {
1419 	return SANE_STATUS_UNSUPPORTED;
1420     }
1421 
1422     return SANE_STATUS_GOOD;
1423 }
1424 
1425 /**
1426  * Obtain a file-descriptor for the scanner that is readable if image data is
1427  * available. The select file-descriptor is returned in *fd.
1428  * The function has not been implemented since USB-device only operate in
1429  * blocking mode.
1430  *
1431  * @param handle Scanner handle
1432  * @param fd File descriptor with imae data
1433  * @return SANE_STATUS_INVAL
1434  */
1435 SANE_Status
sane_get_select_fd(SANE_Handle handle,SANE_Int * fd)1436 sane_get_select_fd (SANE_Handle handle, SANE_Int * fd)
1437 {
1438     DBG(DBG_info_sane,"sane_get_select_fd(): not supported (only for non-blocking IO)\n");
1439     (void) handle;
1440     (void) fd;
1441     return SANE_STATUS_UNSUPPORTED;
1442 }
1443