summaryrefslogtreecommitdiff
path: root/backend/p5_device.h
blob: 4582256beb968a4710b77c4cbe9e864993a114d6 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
/* sane - Scanner Access Now Easy.

   Copyright (C) 2009-2012 stef.dev@free.fr
   
   This program is free software; you can redistribute it and/or
   modify it under the terms of the GNU General Public License as
   published by the Free Software Foundation; either version 2 of the
   License, or (at your option) any later version.
   
   This program is distributed in the hope that it will be useful, but
   WITHOUT ANY WARRANTY; without even the implied warranty of
   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
   General Public License for more details.
   
   You should have received a copy of the GNU General Public License
   along with this program; if not, write to the Free Software
   Foundation, Inc., 59 Temple Place - Suite 330, Boston,
   MA 02111-1307, USA.
*/

/** @file p5_device.h
 * @brief Declaration of low level structures used by the p5 backend.
 *
 * The structures and function declared here are used to do the low level
 * communication with the physical device.
 */

#ifndef P5_DEVICE_H
#define P5_DEVICE_H

#include <stdlib.h>
#include <stdio.h>
#include <string.h>
#include "../include/_stdint.h"

#ifdef HAVE_LINUX_PPDEV_H
#include <errno.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <sys/ioctl.h>
#include <linux/ppdev.h>
#include <linux/parport.h>
#endif

/** @name debugging levels
 */
/* @{ */
#define DBG_error0      0	/* errors/warnings printed even with devuglevel 0 */
#define DBG_error       1	/* fatal errors */
#define DBG_warn        2	/* warnings and non-fatal errors */
#define DBG_info        4	/* informational messages */
#define DBG_proc        8	/* starting/finishing functions */
#define DBG_trace       16	/* tracing messages */
#define DBG_io          32	/* io functions */
#define DBG_io2         64	/* io functions that are called very often */
#define DBG_data        128	/* log image data */
/* @} */

/**
 * maximal number of resolutions
 */
#define MAX_RESOLUTIONS 8

/**> sensor's number of pixels 8.5' @ 300 dpi */
#define MAX_SENSOR_PIXELS     2550

/**> number of lines to skip when doing calibration */
#define CALIBRATION_SKIP_LINES 80

/**> last value considered as black for calibration */
#define BLACK_LEVEL 40

/**> white target value for calibration */
#define WHITE_TARGET 220.0

/** per dpi calibration rgb data
 * Calibration data structure
 */
typedef struct P5_Calibration_Data
{
  unsigned int dpi;
  uint8_t black_data[MAX_SENSOR_PIXELS * 3];
  uint8_t white_data[MAX_SENSOR_PIXELS * 3];
} P5_Calibration_Data;

/** 
 * This structure describes a particular model which is handled by the backend. 
 * Contained data is immutable and is used to initalize the P5_Device
 * structure.
 */
typedef struct P5_Model
{
  /** @name device identifier
   * These values are set up once the physical device has been detected. They
   * are used to build the return value of sane_get_devices().
   */
  /* @{ */
  SANE_String_Const name;
  SANE_String_Const vendor;
  SANE_String_Const product;
  SANE_String_Const type;
  /* @} */

  /** @name resolution
   * list of avalailable physical resolution.
   * The resolutions must sorted from lower to higher value. The list is terminated
   * by a value of 0.
   */
  /* @{ */
  int xdpi_values[MAX_RESOLUTIONS];	/** possible x resolutions */
  int ydpi_values[MAX_RESOLUTIONS];	/** possible y resolutions */
  /* @} */

  /** @name scan area description
   * Minimal and maximal values. It's easier to have dedicated members instead
   * of searching these values in the dpi lists. They are initialized from dpi
   * lists.
   */
  /* @{ */
  int max_xdpi;		/** physical maximum x dpi */
  int max_ydpi;		/** physical maximum y dpi */
  int min_xdpi;		/** physical minimum x dpi */
  int min_ydpi;		/** physical minimum y dpi */
  /* @} */

  /** @name line distance shift
   * Distance between CCD arrays for each color. Expressed in line
   * number at maximum motor resolution.
   */
  int lds;

  /** @name scan area description
   * The geometry values are expressed from the head parking position,
   * or the start. For a given model, the scan area selected by a frontend
   * will have to fit within these values.
   */
  /* @{ */
  SANE_Fixed x_offset;		/** Start of scan area in mm */
  SANE_Fixed y_offset;		/** Start of scan area in mm */
  SANE_Fixed x_size;		/** Size of scan area in mm */
  SANE_Fixed y_size;		/** Size of scan area in mm */
  /* @} */

} P5_Model;


/**
 * Enumeration of configuration options for a device. It must starts at 0.
 */
enum P5_Configure_Option
{
  CFG_MODEL_NAME = 0,		/**<option to override model name */
  NUM_CFG_OPTIONS		/** MUST be last to give the actual number of configuration options */
};

/**
 * Device specific configuration structure to hold option values for
 * devices handled by the p5 backend. There must one member for
 * each configuration option.
 */
typedef struct P5_Config
{
  SANE_String modelname;	/** model name to use, overrinding the one from detection */
} P5_Config;


/**
 * Hardware device description.
 * Since the settings used for a scan may actually differ from the one of the
 * SANE level, it may contains scanning parameters and data relative to a current
 * scan such as data buffers and counters.
 */
typedef struct P5_Device
{
  /**
   * Point to the next device in a linked list
   */
  struct P5_Device *next;

  /**
   * Points to a structure that decribes model capabilities, geometry 
   * and default settings.
   */
  P5_Model *model;

  /**
   * @brief name of the device
   * Name of the device: it may be the file name used to access the hardware.
   * For instance parport0 for a parallel port device, or the libusb file name
   * for an USB scanner.
   */
  SANE_String name;

  /**
   * SANE_TRUE if the device is local (ie not over network)
   */
  SANE_Bool local;

  /**
   * True if device has been intialized.
   */
  SANE_Bool initialized;

  /**
   * Configuration options for the device read from
   * configuration file at attach time. This member is filled at 
   * attach time.
   */
  P5_Config *config;

  /** @brief scan parameters
   * The scan done by the hardware can be different from the one at the SANE
   * frontend session. For instance: 
   *  - xdpy and ydpi may be different to accomodate hardware capabilites.
   *  - many CCD scanners need to scan more lines to correct the 'line 
   *  distance shift' effect.
   *  - emulated modes (lineart from gray scan, or gray scan for color one)
   */
  /* @{ */
  int xdpi;		/** real horizontal resolution */
  int ydpi;		/** real vertical resolution */
  int lines;		/** physical lines to scan */
  int pixels;		/** physical width of scan area */
  int bytes_per_line;	/** number of bytes per line */
  int xstart;		/** x start coordinate */
  int ystart;		/** y start coordinate */
  int mode;		/** color, gray or lineart mode */
  int lds;		/** line distance shift */
  /* @} */

  /** @brief device file descriptor
   * low level device file descriptor
   */
  int fd;

  /**
   * work buffer for scans
   */
  uint8_t *buffer;

  /**
   * buffer size
   */
  size_t size;

  /**
   * position in buffer
   */
  size_t position;

  /**
   * top value of available bytes in buffer
   */
  size_t top;

  /**
   * bottom value of available bytes in buffer
   */
  size_t bottom;

  /**
   * True if device has been calibrated.
   */
  SANE_Bool calibrated;

  P5_Calibration_Data *calibration_data[MAX_RESOLUTIONS * 2];

  /**> correction coefficient for the current scan */
  float *gain;
  uint8_t *offset;

} P5_Device;


#define DATA    0
#define STATUS  1
#define CONTROL 2
#define EPPADR  3
#define EPPDATA 4

#define REG0 0x00
#define REG1 0x11
#define REG2 0x22
#define REG3 0x33
#define REG4 0x44
#define REG5 0x55
#define REG6 0x66
#define REG7 0x77
#define REG8 0x88
#define REG9 0x99
#define REGA 0xAA
#define REGB 0xBB
#define REGC 0xCC
#define REGD 0xDD
#define REGE 0xEE
#define REGF 0xFF

#define MODE_COLOR 	0
#define MODE_GRAY  	1
#define MODE_LINEART    2

#endif /* not P5_DEVICE_H */

/* vim: set sw=2 cino=>2se-1sn-1s{s^-1st0(0u0 smarttab expandtab: */