1/* HP Scanjet 3900 series - RTS8822 Core 2 3 Copyright (C) 2005-2013 Jonathan Bravo Lopez <jkdsoft@gmail.com> 4 5 This file is part of the SANE package. 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 9 as published by the Free Software Foundation; either version 2 10 of the License, or (at your option) any later version. 11 12 This program is distributed in the hope that it will be useful, 13 but WITHOUT ANY WARRANTY; without even the implied warranty of 14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 15 GNU 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/* 44 This code is still a bit ugly due to it's the result of applying 45 reverse engineering techniques to windows driver. So at this 46 moment what you see is exactly what windows driver does. 47 And so many global vars exist that will be erased when driver 48 is entirely debugged. There are some variables with unknown 49 purpose. So they have no meaning name in form v+address. I 50 hope to change their names when driver is debugged completely. 51*/ 52 53#ifndef RTS8822_CORE 54 55#define RTS8822_CORE 56 57#define GetTickCount() (time(0) * 1000) 58#define min(A,B) (((A)<(B)) ? (A) : (B)) 59#define max(A,B) (((A)>(B)) ? (A) : (B)) 60#define PIXEL_TO_MM(_pixel_, _dpi_) ((_pixel_) * 25.4 / (_dpi_)) 61#define MM_TO_PIXEL(_mm_, _dpi_) ((_mm_) * (_dpi_) / 25.4) 62 63#include <stdio.h> 64#include <stdlib.h> 65#include <string.h> /* memset() */ 66#include <time.h> /* clock() */ 67#include <math.h> /* truncf() */ 68#include <ctype.h> /* tolower() */ 69#include <unistd.h> /* usleep() */ 70#include <sys/types.h> 71 72#include "hp3900_types.c" 73#include "hp3900_debug.c" 74#include "hp3900_config.c" 75#include "hp3900_usb.c" 76 77/*-------------------- Exported function headers --------------------*/ 78 79#ifdef developing 80static SANE_Int hp4370_prueba (struct st_device *dev); 81static void prueba (SANE_Byte * a); 82void shadingtest1 (struct st_device *dev, SANE_Byte * Regs, 83 struct st_calibration *myCalib); 84static SANE_Int Calib_test (struct st_device *dev, SANE_Byte * Regs, 85 struct st_calibration *myCalib, 86 struct st_scanparams *scancfg); 87static SANE_Int Calib_BlackShading_jkd (struct st_device *dev, 88 SANE_Byte * Regs, 89 struct st_calibration *myCalib, 90 struct st_scanparams *scancfg); 91#endif 92 93/*static void show_diff(struct st_device *dev, SANE_Byte *original);*/ 94 95/* functions to allocate and free space for a device */ 96static struct st_device *RTS_Alloc (void); 97static void RTS_Free (struct st_device *dev); 98 99/* Scanner level commands */ 100static SANE_Int RTS_Scanner_Init (struct st_device *dev); 101static SANE_Int RTS_Scanner_SetParams (struct st_device *dev, 102 struct params *param); 103static SANE_Int RTS_Scanner_StartScan (struct st_device *dev); 104static void RTS_Scanner_StopScan (struct st_device *dev, SANE_Int wait); 105static void RTS_Scanner_End (struct st_device *dev); 106 107/* loading configuration functions */ 108static SANE_Int Load_Buttons (struct st_device *dev); 109static SANE_Int Load_Chipset (struct st_device *dev); 110static SANE_Int Load_Config (struct st_device *dev); 111static SANE_Int Load_Constrains (struct st_device *dev); 112static SANE_Int Load_Motor (struct st_device *dev); 113static SANE_Int Load_MotorCurves (struct st_device *dev); 114static SANE_Int Load_Motormoves (struct st_device *dev); 115static SANE_Int Load_Scanmodes (struct st_device *dev); 116static SANE_Int Load_Sensor (struct st_device *dev); 117static SANE_Int Load_Timings (struct st_device *dev); 118 119/* freeing configuration functions */ 120static void Free_Buttons (struct st_device *dev); 121static void Free_Chipset (struct st_device *dev); 122static void Free_Config (struct st_device *dev); 123static void Free_Constrains (struct st_device *dev); 124static void Free_Motor (struct st_device *dev); 125static void Free_MotorCurves (struct st_device *dev); 126static void Free_Motormoves (struct st_device *dev); 127static void Free_Scanmodes (struct st_device *dev); 128static void Free_Sensor (struct st_device *dev); 129static void Free_Timings (struct st_device *dev); 130static void Free_Vars (void); 131 132/* Functions to manage data */ 133static SANE_Byte data_bitget (SANE_Byte * address, SANE_Int mask); 134static void data_bitset (SANE_Byte * address, SANE_Int mask, SANE_Byte data); 135static SANE_Int data_lsb_get (SANE_Byte * address, SANE_Int size); 136static void data_lsb_set (SANE_Byte * address, SANE_Int data, SANE_Int size); 137static void data_msb_set (SANE_Byte * address, SANE_Int data, SANE_Int size); 138static void data_wide_bitset (SANE_Byte * address, SANE_Int mask, 139 SANE_Int data); 140static SANE_Int data_swap_endianess (SANE_Int address, SANE_Int size); 141 142static SANE_Int Device_get (SANE_Int product, SANE_Int vendor); 143 144/* Chipset related commands */ 145static SANE_Int Chipset_ID (struct st_device *dev); 146static SANE_Int Chipset_Name (struct st_device *dev, char *name, 147 SANE_Int size); 148static SANE_Int Chipset_Reset (struct st_device *dev); 149 150/* Initializing functions */ 151static SANE_Int Init_Registers (struct st_device *dev); 152static SANE_Int Init_USBData (struct st_device *dev); 153static SANE_Int Init_Vars (void); 154 155/* scanmode functions */ 156static SANE_Int Scanmode_fitres (struct st_device *dev, SANE_Int scantype, 157 SANE_Int colormode, SANE_Int resolution); 158static SANE_Int Scanmode_maxres (struct st_device *dev, SANE_Int scantype, 159 SANE_Int colormode); 160static SANE_Int Scanmode_minres (struct st_device *dev, SANE_Int scantype, 161 SANE_Int colormode); 162 163/* Chipset management useful commands*/ 164static SANE_Int RTS_USBType (struct st_device *dev); 165static SANE_Byte RTS_Sensor_Type (USB_Handle usb_handle); 166static void RTS_DebugInit (void); 167static SANE_Int RTS_Enable_CCD (struct st_device *dev, SANE_Byte * Regs, 168 SANE_Int channels); 169 170/* DMA management commands */ 171static SANE_Int RTS_DMA_Cancel (struct st_device *dev); 172static SANE_Int RTS_DMA_CheckType (struct st_device *dev, SANE_Byte * Regs); 173static SANE_Int RTS_DMA_Enable_Read (struct st_device *dev, SANE_Int dmacs, 174 SANE_Int size, SANE_Int options); 175static SANE_Int RTS_DMA_Enable_Write (struct st_device *dev, SANE_Int dmacs, 176 SANE_Int size, SANE_Int options); 177static SANE_Int RTS_DMA_Read (struct st_device *dev, SANE_Int dmacs, 178 SANE_Int options, SANE_Int size, 179 SANE_Byte * buffer); 180static SANE_Int RTS_DMA_Reset (struct st_device *dev); 181static SANE_Int RTS_DMA_SetType (struct st_device *dev, SANE_Byte * Regs, 182 SANE_Byte ramtype); 183static SANE_Int RTS_DMA_WaitReady (struct st_device *dev, SANE_Int msecs); 184static SANE_Int RTS_DMA_Write (struct st_device *dev, SANE_Int dmacs, 185 SANE_Int options, SANE_Int size, 186 SANE_Byte * buffer); 187 188/* EEPROM management commands */ 189static SANE_Int RTS_EEPROM_ReadByte (USB_Handle usb_handle, SANE_Int address, 190 SANE_Byte * data); 191static SANE_Int RTS_EEPROM_ReadInteger (USB_Handle usb_handle, 192 SANE_Int address, SANE_Int * data); 193static SANE_Int RTS_EEPROM_ReadWord (USB_Handle usb_handle, SANE_Int address, 194 SANE_Int * data); 195static SANE_Int RTS_EEPROM_WriteBuffer (USB_Handle usb_handle, 196 SANE_Int address, SANE_Byte * data, 197 SANE_Int size); 198static SANE_Int RTS_EEPROM_WriteByte (USB_Handle usb_handle, SANE_Int address, 199 SANE_Byte data); 200static SANE_Int RTS_EEPROM_WriteInteger (USB_Handle usb_handle, 201 SANE_Int address, SANE_Int data); 202static SANE_Int RTS_EEPROM_WriteWord (USB_Handle usb_handle, SANE_Int address, 203 SANE_Int data); 204 205static SANE_Int RTS_Execute (struct st_device *dev); 206static SANE_Int RTS_Warm_Reset (struct st_device *dev); 207static SANE_Byte RTS_IsExecuting (struct st_device *dev, SANE_Byte * Regs); 208 209static SANE_Int RTS_GetScanmode (struct st_device *dev, SANE_Int scantype, 210 SANE_Int colormode, SANE_Int resolution); 211static SANE_Int RTS_GetImage (struct st_device *dev, SANE_Byte * Regs, 212 struct st_scanparams *scancfg, 213 struct st_gain_offset *gain_offset, 214 SANE_Byte * buffer, 215 struct st_calibration *myCalib, 216 SANE_Int options, SANE_Int gainmode); 217static SANE_Int RTS_GetImage_GetBuffer (struct st_device *dev, double dSize, 218 SANE_Byte * buffer, 219 double *transferred); 220static SANE_Int RTS_GetImage_Read (struct st_device *dev, SANE_Byte * buffer, 221 struct st_scanparams *myvar, 222 struct st_hwdconfig *hwdcfg); 223 224static SANE_Int RTS_isTmaAttached (struct st_device *dev); 225 226/* functions to wait for a process tp finish */ 227static SANE_Int RTS_WaitInitEnd (struct st_device *dev, SANE_Int msecs); 228static SANE_Int RTS_WaitScanEnd (struct st_device *dev, SANE_Int msecs); 229 230/* functions to read/write control registers */ 231static SANE_Int RTS_ReadRegs (USB_Handle usb_handle, SANE_Byte * buffer); 232static SANE_Int RTS_WriteRegs (USB_Handle usb_handle, SANE_Byte * buffer); 233 234/* functions to manage the scan counter */ 235static SANE_Int RTS_ScanCounter_Inc (struct st_device *dev); 236static SANE_Int RTS_ScanCounter_Get (struct st_device *dev); 237 238/* functions to setup control registers */ 239static SANE_Int RTS_Setup (struct st_device *dev, SANE_Byte * Regs, 240 struct st_scanparams *myvar, 241 struct st_hwdconfig *hwdcfg, 242 struct st_gain_offset *gain_offset); 243static void RTS_Setup_Arrangeline (struct st_device *dev, 244 struct st_hwdconfig *hwdcfg, 245 SANE_Int colormode); 246static void RTS_Setup_Channels (struct st_device *dev, SANE_Byte * Regs, 247 struct st_scanparams *scancfg, 248 SANE_Int mycolormode); 249static void RTS_Setup_Coords (SANE_Byte * Regs, SANE_Int iLeft, SANE_Int iTop, 250 SANE_Int width, SANE_Int height); 251static SANE_Int RTS_Setup_Depth (SANE_Byte * Regs, 252 struct st_scanparams *scancfg, 253 SANE_Int mycolormode); 254static void RTS_Setup_Exposure_Times (SANE_Byte * Regs, 255 struct st_scanparams *scancfg, 256 struct st_scanmode *sm); 257static void RTS_Setup_GainOffset (SANE_Byte * Regs, 258 struct st_gain_offset *gain_offset); 259static void RTS_Setup_Gamma (SANE_Byte * Regs, struct st_hwdconfig *lowcfg); 260static SANE_Int RTS_Setup_Line_Distances (struct st_device *dev, 261 SANE_Byte * Regs, 262 struct st_scanparams *scancfg, 263 struct st_hwdconfig *hwdcfg, 264 SANE_Int mycolormode, 265 SANE_Int arrangeline); 266static SANE_Int RTS_Setup_Motor (struct st_device *dev, SANE_Byte * Regs, 267 struct st_scanparams *myvar, 268 SANE_Int somevalue); 269static void RTS_Setup_RefVoltages (struct st_device *dev, SANE_Byte * Regs); 270static void RTS_Setup_SensorTiming (struct st_device *dev, SANE_Int mytiming, 271 SANE_Byte * Regs); 272static void RTS_Setup_Shading (SANE_Byte * Regs, 273 struct st_scanparams *scancfg, 274 struct st_hwdconfig *hwdcfg, 275 SANE_Int bytes_per_line); 276 277static SANE_Int Scan_Start (struct st_device *dev); 278 279static void SetLock (USB_Handle usb_handle, SANE_Byte * Regs, 280 SANE_Byte Enable); 281static SANE_Int fn3330 (struct st_device *dev, SANE_Byte * Regs, 282 struct st_cal2 *calbuffers, 283 SANE_Int sensorchannelcolor, SANE_Int * tablepos, 284 SANE_Int data); 285static SANE_Int fn3560 (USHORT * table, struct st_cal2 *calbuffers, 286 SANE_Int * tablepos); 287static SANE_Int fn3730 (struct st_device *dev, struct st_cal2 *calbuffers, 288 SANE_Byte * Regs, USHORT * table, 289 SANE_Int sensorchannelcolor, SANE_Int data); 290 291static SANE_Int Reading_CreateBuffers (struct st_device *dev); 292static SANE_Int Reading_DestroyBuffers (struct st_device *dev); 293static SANE_Int Reading_BufferSize_Get (struct st_device *dev, 294 SANE_Byte channels_per_dot, 295 SANE_Int channel_size); 296static SANE_Int Reading_BufferSize_Notify (struct st_device *dev, 297 SANE_Int data, SANE_Int size); 298static SANE_Int Reading_Wait (struct st_device *dev, 299 SANE_Byte Channels_per_dot, 300 SANE_Byte Channel_size, SANE_Int size, 301 SANE_Int * last_amount, SANE_Int seconds, 302 SANE_Byte op); 303 304static SANE_Int Read_Image (struct st_device *dev, SANE_Int buffer_size, 305 SANE_Byte * buffer, SANE_Int * transferred); 306static SANE_Int Read_ResizeBlock (struct st_device *dev, SANE_Byte * buffer, 307 SANE_Int buffer_size, 308 SANE_Int * transferred); 309static SANE_Int Read_Block (struct st_device *dev, SANE_Int buffer_size, 310 SANE_Byte * buffer, SANE_Int * transferred); 311static SANE_Int Read_NonColor_Block (struct st_device *dev, 312 SANE_Byte * buffer, SANE_Int buffer_size, 313 SANE_Byte ColorMode, 314 SANE_Int * transferred); 315 316/* Ref functions */ 317static SANE_Int Refs_Analyze_Pattern (struct st_scanparams *scancfg, 318 SANE_Byte * scanned_pattern, 319 SANE_Int * ler1, SANE_Int ler1order, 320 SANE_Int * ser1, SANE_Int ser1order); 321static SANE_Int Refs_Counter_Inc (struct st_device *dev); 322static SANE_Byte Refs_Counter_Load (struct st_device *dev); 323static SANE_Int Refs_Counter_Save (struct st_device *dev, SANE_Byte data); 324static SANE_Int Refs_Detect (struct st_device *dev, SANE_Byte * Regs, 325 SANE_Int resolution_x, SANE_Int resolution_y, 326 SANE_Int * x, SANE_Int * y); 327static SANE_Int Refs_Load (struct st_device *dev, SANE_Int * x, SANE_Int * y); 328static SANE_Int Refs_Save (struct st_device *dev, SANE_Int left_leading, 329 SANE_Int start_pos); 330static SANE_Int Refs_Set (struct st_device *dev, SANE_Byte * Regs, 331 struct st_scanparams *myscan); 332 333/* Coordinates' constrains functions */ 334static SANE_Int Constrains_Check (struct st_device *dev, SANE_Int Resolution, 335 SANE_Int scantype, 336 struct st_coords *mycoords); 337static struct st_coords *Constrains_Get (struct st_device *dev, 338 SANE_Byte scantype); 339 340/* Gain and offset functions */ 341static SANE_Int GainOffset_Clear (struct st_device *dev); 342static SANE_Int GainOffset_Get (struct st_device *dev); 343static SANE_Int GainOffset_Save (struct st_device *dev, SANE_Int * offset, 344 SANE_Byte * gain); 345static SANE_Int GainOffset_Counter_Inc (struct st_device *dev, 346 SANE_Int * arg1); 347static SANE_Byte GainOffset_Counter_Load (struct st_device *dev); 348static SANE_Int GainOffset_Counter_Save (struct st_device *dev, 349 SANE_Byte data); 350 351/* Gamma functions*/ 352static SANE_Int Gamma_AllocTable (SANE_Byte * table); 353static SANE_Int Gamma_Apply (struct st_device *dev, SANE_Byte * Regs, 354 struct st_scanparams *scancfg, 355 struct st_hwdconfig *hwdcfg, 356 struct st_gammatables *mygamma); 357static void Gamma_FreeTables (void); 358static SANE_Int Gamma_SendTables (struct st_device *dev, SANE_Byte * Regs, 359 SANE_Byte * gammatable, SANE_Int size); 360static SANE_Int Gamma_GetTables (struct st_device *dev, 361 SANE_Byte * Gamma_buffer); 362 363/* Lamp functions */ 364static SANE_Byte Lamp_GetGainMode (struct st_device *dev, SANE_Int resolution, 365 SANE_Byte scantype); 366static void Lamp_SetGainMode (struct st_device *dev, SANE_Byte * Regs, 367 SANE_Int resolution, SANE_Byte gainmode); 368static SANE_Int Lamp_PWM_DutyCycle_Get (struct st_device *dev, 369 SANE_Int * data); 370static SANE_Int Lamp_PWM_DutyCycle_Set (struct st_device *dev, 371 SANE_Int duty_cycle); 372static SANE_Int Lamp_PWM_Setup (struct st_device *dev, SANE_Int lamp); 373static SANE_Int Lamp_PWM_use (struct st_device *dev, SANE_Int enable); 374static SANE_Int Lamp_PWM_CheckStable (struct st_device *dev, 375 SANE_Int resolution, SANE_Int lamp); 376static SANE_Int Lamp_PWM_Save (struct st_device *dev, SANE_Int fixedpwm); 377static SANE_Int Lamp_PWM_SaveStatus (struct st_device *dev, SANE_Byte status); 378static SANE_Int Lamp_Status_Get (struct st_device *dev, SANE_Byte * flb_lamp, 379 SANE_Byte * tma_lamp); 380static SANE_Int Lamp_Status_Set (struct st_device *dev, SANE_Byte * Regs, 381 SANE_Int turn_on, SANE_Int lamp); 382static SANE_Int Lamp_Status_Timer_Set (struct st_device *dev, 383 SANE_Int minutes); 384static SANE_Int Lamp_Warmup (struct st_device *dev, SANE_Byte * Regs, 385 SANE_Int lamp, SANE_Int resolution); 386 387/* Head related functions */ 388static SANE_Int Head_IsAtHome (struct st_device *dev, SANE_Byte * Regs); 389static SANE_Int Head_ParkHome (struct st_device *dev, SANE_Int bWait, 390 SANE_Int movement); 391static SANE_Int Head_Relocate (struct st_device *dev, SANE_Int speed, 392 SANE_Int direction, SANE_Int ypos); 393 394/* Motor functions */ 395static SANE_Byte *Motor_AddStep (SANE_Byte * steps, SANE_Int * bwriten, 396 SANE_Int step); 397static SANE_Int Motor_Change (struct st_device *dev, SANE_Byte * buffer, 398 SANE_Byte value); 399static SANE_Int Motor_GetFromResolution (SANE_Int resolution); 400static SANE_Int Motor_Move (struct st_device *dev, SANE_Byte * Regs, 401 struct st_motormove *mymotor, 402 struct st_motorpos *mtrpos); 403static void Motor_Release (struct st_device *dev); 404static SANE_Int Motor_Setup_Steps (struct st_device *dev, SANE_Byte * Regs, 405 SANE_Int mysetting); 406static SANE_Int Motor_Curve_Equal (struct st_device *dev, 407 SANE_Int motorsetting, SANE_Int direction, 408 SANE_Int curve1, SANE_Int curve2); 409static void Motor_Curve_Free (struct st_motorcurve **motorcurves, 410 SANE_Int * mtc_count); 411static struct st_curve *Motor_Curve_Get (struct st_device *dev, 412 SANE_Int motorcurve, 413 SANE_Int direction, SANE_Int itype); 414static struct st_motorcurve **Motor_Curve_Parse (SANE_Int * mtc_count, 415 SANE_Int * buffer); 416 417/* Functions to arrange scanned lines */ 418static SANE_Int Arrange_Colour (struct st_device *dev, SANE_Byte * buffer, 419 SANE_Int buffer_size, SANE_Int * transferred); 420static SANE_Int Arrange_Compose (struct st_device *dev, SANE_Byte * buffer, 421 SANE_Int buffer_size, 422 SANE_Int * transferred); 423static SANE_Int Arrange_NonColour (struct st_device *dev, SANE_Byte * buffer, 424 SANE_Int buffer_size, 425 SANE_Int * transferred); 426 427/* Composing RGB triplet functions */ 428static void Triplet_Gray (SANE_Byte * pPointer1, SANE_Byte * pPointer2, 429 SANE_Byte * buffer, SANE_Int channels_count); 430static void Triplet_Lineart (SANE_Byte * pPointer1, SANE_Byte * pPointer2, 431 SANE_Byte * buffer, SANE_Int channels_count); 432static void Triplet_Compose_Order (struct st_device *dev, SANE_Byte * pRed, 433 SANE_Byte * pGreen, SANE_Byte * pBlue, 434 SANE_Byte * buffer, SANE_Int dots); 435static void Triplet_Compose_HRes (SANE_Byte * pPointer1, 436 SANE_Byte * pPointer2, 437 SANE_Byte * pPointer3, 438 SANE_Byte * pPointer4, 439 SANE_Byte * pPointer5, 440 SANE_Byte * pPointer6, SANE_Byte * buffer, 441 SANE_Int Width); 442static void Triplet_Compose_LRes (SANE_Byte * pRed, SANE_Byte * pGreen, 443 SANE_Byte * pBlue, SANE_Byte * buffer, 444 SANE_Int dots); 445static void Triplet_Colour_Order (struct st_device *dev, SANE_Byte * pRed, 446 SANE_Byte * pGreen, SANE_Byte * pBlue, 447 SANE_Byte * buffer, SANE_Int Width); 448static void Triplet_Colour_HRes (SANE_Byte * pRed1, SANE_Byte * pGreen1, 449 SANE_Byte * pBlue1, SANE_Byte * pRed2, 450 SANE_Byte * pGreen2, SANE_Byte * pBlue2, 451 SANE_Byte * buffer, SANE_Int Width); 452static void Triplet_Colour_LRes (SANE_Int Width, SANE_Byte * Buffer, 453 SANE_Byte * pChannel1, SANE_Byte * pChannel2, 454 SANE_Byte * pChannel3); 455 456/* Timing functions */ 457static SANE_Int Timing_SetLinearImageSensorClock (SANE_Byte * Regs, 458 struct st_cph *cph); 459 460/* Functions used to resize retrieved image */ 461static SANE_Int Resize_Start (struct st_device *dev, SANE_Int * transferred); 462static SANE_Int Resize_CreateBuffers (struct st_device *dev, SANE_Int size1, 463 SANE_Int size2, SANE_Int size3); 464static SANE_Int Resize_DestroyBuffers (struct st_device *dev); 465static SANE_Int Resize_Increase (SANE_Byte * to_buffer, 466 SANE_Int to_resolution, SANE_Int to_width, 467 SANE_Byte * from_buffer, 468 SANE_Int from_resolution, 469 SANE_Int from_width, SANE_Int myresize_mode); 470static SANE_Int Resize_Decrease (SANE_Byte * to_buffer, 471 SANE_Int to_resolution, SANE_Int to_width, 472 SANE_Byte * from_buffer, 473 SANE_Int from_resolution, 474 SANE_Int from_width, SANE_Int myresize_mode); 475 476/* Scanner buttons support */ 477static SANE_Int Buttons_Count (struct st_device *dev); 478static SANE_Int Buttons_Enable (struct st_device *dev); 479static SANE_Int Buttons_Order (struct st_device *dev, SANE_Int mask); 480static SANE_Int Buttons_Status (struct st_device *dev); 481static SANE_Int Buttons_Released (struct st_device *dev); 482 483/* Calibration functions */ 484static SANE_Int Calib_CreateBuffers (struct st_device *dev, 485 struct st_calibration *buffer, 486 SANE_Int my14b4); 487static SANE_Int Calib_CreateFixedBuffers (void); 488static void Calib_FreeBuffers (struct st_calibration *caltables); 489static void Calib_LoadCut (struct st_device *dev, 490 struct st_scanparams *scancfg, SANE_Int scantype, 491 struct st_calibration_config *calibcfg); 492static SANE_Int Calib_AdcGain (struct st_device *dev, 493 struct st_calibration_config *calibcfg, 494 SANE_Int arg2, SANE_Int gainmode); 495static SANE_Int Calib_AdcOffsetRT (struct st_device *dev, 496 struct st_calibration_config *calibcfg, 497 SANE_Int value); 498static SANE_Int Calib_BlackShading (struct st_device *dev, 499 struct st_calibration_config *calibcfg, 500 struct st_calibration *myCalib, 501 SANE_Int gainmode); 502static SANE_Int Calib_BWShading (struct st_calibration_config *calibcfg, 503 struct st_calibration *myCalib, 504 SANE_Int gainmode); 505static SANE_Int Calib_WhiteShading_3 (struct st_device *dev, 506 struct st_calibration_config *calibcfg, 507 struct st_calibration *myCalib, 508 SANE_Int gainmode); 509static void Calibrate_Free (struct st_cal2 *calbuffers); 510static SANE_Int Calibrate_Malloc (struct st_cal2 *calbuffers, 511 SANE_Byte * Regs, 512 struct st_calibration *myCalib, 513 SANE_Int somelength); 514static SANE_Int Calib_ReadTable (struct st_device *dev, SANE_Byte * table, 515 SANE_Int size, SANE_Int data); 516static SANE_Int Calib_WriteTable (struct st_device *dev, SANE_Byte * table, 517 SANE_Int size, SANE_Int data); 518static SANE_Int Calib_LoadConfig (struct st_device *dev, 519 struct st_calibration_config *calibcfg, 520 SANE_Int scantype, SANE_Int resolution, 521 SANE_Int bitmode); 522static SANE_Int Calib_PAGain (struct st_device *dev, 523 struct st_calibration_config *calibcfg, 524 SANE_Int gainmode); 525static SANE_Int Calibration (struct st_device *dev, SANE_Byte * Regs, 526 struct st_scanparams *scancfg, 527 struct st_calibration *myCalib, SANE_Int value); 528 529/* function for white shading correction */ 530static SANE_Int WShading_Calibrate (struct st_device *dev, SANE_Byte * Regs, 531 struct st_calibration *myCalib, 532 struct st_scanparams *scancfg); 533static void WShading_Emulate (SANE_Byte * buffer, SANE_Int * chnptr, 534 SANE_Int size, SANE_Int depth); 535 536/* functions for shading calibration */ 537static SANE_Int Shading_apply (struct st_device *dev, SANE_Byte * Regs, 538 struct st_scanparams *myvar, 539 struct st_calibration *myCalib); 540static SANE_Int Shading_black_apply (struct st_device *dev, SANE_Byte * Regs, 541 SANE_Int channels, 542 struct st_calibration *myCalib, 543 struct st_cal2 *calbuffers); 544static SANE_Int Shading_white_apply (struct st_device *dev, SANE_Byte * Regs, 545 SANE_Int channels, 546 struct st_calibration *myCalib, 547 struct st_cal2 *calbuffers); 548 549/* Spread-Spectrum Clock Generator functions */ 550static SANE_Int SSCG_Enable (struct st_device *dev); 551 552static void Split_into_12bit_channels (SANE_Byte * destino, 553 SANE_Byte * fuente, SANE_Int size); 554static SANE_Int Scan_Read_BufferA (struct st_device *dev, 555 SANE_Int buffer_size, SANE_Int arg2, 556 SANE_Byte * pBuffer, 557 SANE_Int * bytes_transferred); 558 559static SANE_Int Bulk_Operation (struct st_device *dev, SANE_Byte op, 560 SANE_Int buffer_size, SANE_Byte * buffer, 561 SANE_Int * transferred); 562static SANE_Int Get_PAG_Value (SANE_Byte scantype, SANE_Byte color); 563static SANE_Int GetOneLineInfo (struct st_device *dev, SANE_Int resolution, 564 SANE_Int * maximus, SANE_Int * minimus, 565 double *average); 566 567static SANE_Int Load_StripCoords (SANE_Int scantype, SANE_Int * ypos, 568 SANE_Int * xpos); 569 570/*static SANE_Int Free_Fixed_CalBuffer(void);*/ 571static SANE_Int SetMultiExposure (struct st_device *dev, SANE_Byte * Regs); 572 573static void Set_E950_Mode (struct st_device *dev, SANE_Byte mode); 574 575static SANE_Int LoadImagingParams (struct st_device *dev, SANE_Int inifile); 576 577static SANE_Int SetScanParams (struct st_device *dev, SANE_Byte * Regs, 578 struct st_scanparams *scancfg, 579 struct st_hwdconfig *hwdcfg); 580static SANE_Int IsScannerLinked (struct st_device *dev); 581 582static SANE_Int Read_FE3E (struct st_device *dev, SANE_Byte * destino); 583 584static double get_shrd (double value, SANE_Int desp); 585static char get_byte (double value); 586/*static SANE_Int RTS8822_GetRegisters(SANE_Byte *buffer);*/ 587 588/* ----------------- Implementation ------------------*/ 589 590static void 591RTS_Free (struct st_device *dev) 592{ 593 /* this function frees space of devices's variable */ 594 595 if (dev != NULL) 596 { 597 /* next function shouldn't be necessary but I can NOT assure that other 598 programmers will call Free_Config before this function */ 599 Free_Config (dev); 600 601 if (dev->init_regs != NULL) 602 free (dev->init_regs); 603 604 if (dev->Resize != NULL) 605 free (dev->Resize); 606 607 if (dev->Reading != NULL) 608 free (dev->Reading); 609 610 if (dev->scanning != NULL) 611 free (dev->scanning); 612 613 if (dev->status != NULL) 614 free (dev->status); 615 616 free (dev); 617 } 618} 619 620static struct st_device * 621RTS_Alloc () 622{ 623 /* this function allocates space for device's variable */ 624 625 struct st_device *dev = NULL; 626 627 dev = malloc (sizeof (struct st_device)); 628 if (dev != NULL) 629 { 630 SANE_Int rst = OK; 631 632 memset (dev, 0, sizeof (struct st_device)); 633 634 /* initial registers */ 635 dev->init_regs = malloc (sizeof (SANE_Byte) * RT_BUFFER_LEN); 636 if (dev->init_regs != NULL) 637 memset (dev->init_regs, 0, sizeof (SANE_Byte) * RT_BUFFER_LEN); 638 else 639 rst = ERROR; 640 641 if (rst == OK) 642 { 643 dev->scanning = malloc (sizeof (struct st_scanning)); 644 if (dev->scanning != NULL) 645 memset (dev->scanning, 0, sizeof (struct st_scanning)); 646 else 647 rst = ERROR; 648 } 649 650 if (rst == OK) 651 { 652 dev->Reading = malloc (sizeof (struct st_readimage)); 653 if (dev->Reading != NULL) 654 memset (dev->Reading, 0, sizeof (struct st_readimage)); 655 else 656 rst = ERROR; 657 } 658 659 if (rst == OK) 660 { 661 dev->Resize = malloc (sizeof (struct st_resize)); 662 if (dev->Resize != NULL) 663 memset (dev->Resize, 0, sizeof (struct st_resize)); 664 else 665 rst = ERROR; 666 } 667 668 if (rst == OK) 669 { 670 dev->status = malloc (sizeof (struct st_status)); 671 if (dev->status != NULL) 672 memset (dev->status, 0, sizeof (struct st_status)); 673 else 674 rst = ERROR; 675 } 676 677 /* if something fails, free space */ 678 if (rst != OK) 679 { 680 RTS_Free (dev); 681 dev = NULL; 682 } 683 } 684 685 return dev; 686} 687 688static void 689RTS_Scanner_End (struct st_device *dev) 690{ 691 Gamma_FreeTables (); 692 Free_Config (dev); 693 Free_Vars (); 694} 695 696static SANE_Int 697Device_get (SANE_Int product, SANE_Int vendor) 698{ 699 return cfg_device_get (product, vendor); 700} 701 702static SANE_Int 703RTS_Scanner_Init (struct st_device *dev) 704{ 705 SANE_Int rst; 706 707 DBG (DBG_FNC, "> RTS_Scanner_Init:\n"); 708 DBG (DBG_FNC, "> Backend version: %s\n", BACKEND_VRSN); 709 710 rst = ERROR; 711 712 /* gets usb type of this scanner if it's not already set by user */ 713 if (RTS_Debug->usbtype == -1) 714 RTS_Debug->usbtype = RTS_USBType (dev); 715 716 if (RTS_Debug->usbtype != ERROR) 717 { 718 DBG (DBG_FNC, " -> Chipset model ID: %i\n", Chipset_ID (dev)); 719 720 Chipset_Reset (dev); 721 722 if (Load_Config (dev) == OK) 723 { 724 if (IsScannerLinked (dev) == OK) 725 { 726 Set_E950_Mode (dev, 0); 727 Gamma_AllocTable (NULL); 728 rst = OK; 729 } 730 else 731 Free_Config (dev); 732 } 733 } 734 735 return rst; 736} 737 738static SANE_Int 739RTS_WriteRegs (USB_Handle usb_handle, SANE_Byte * buffer) 740{ 741 SANE_Int rst = ERROR; 742 743 if (buffer != NULL) 744 rst = 745 Write_Buffer (usb_handle, 0xe800, buffer, 746 RT_BUFFER_LEN * sizeof (SANE_Byte)); 747 748 return rst; 749} 750 751static SANE_Int 752RTS_ReadRegs (USB_Handle usb_handle, SANE_Byte * buffer) 753{ 754 SANE_Int rst = ERROR; 755 756 if (buffer != NULL) 757 rst = 758 Read_Buffer (usb_handle, 0xe800, buffer, 759 RT_BUFFER_LEN * sizeof (SANE_Byte)); 760 761 return rst; 762} 763 764static void 765SetLock (USB_Handle usb_handle, SANE_Byte * Regs, SANE_Byte Enable) 766{ 767 SANE_Byte lock; 768 769 DBG (DBG_FNC, "+ SetLock(*Regs, Enable=%i):\n", Enable); 770 771 if (Regs == NULL) 772 { 773 if (Read_Byte (usb_handle, 0xee00, &lock) != OK) 774 lock = 0; 775 } 776 else 777 lock = Regs[0x600]; 778 779 if (Enable == FALSE) 780 lock &= 0xfb; 781 else 782 lock |= 4; 783 784 if (Regs != NULL) 785 Regs[0x600] = lock; 786 787 Write_Byte (usb_handle, 0xee00, lock); 788 789 DBG (DBG_FNC, "- SetLock\n"); 790} 791 792static void 793Set_E950_Mode (struct st_device *dev, SANE_Byte mode) 794{ 795 SANE_Int data; 796 797 DBG (DBG_FNC, "+ Set_E950_Mode(mode=%i):\n", mode); 798 799 if (Read_Word (dev->usb_handle, 0xe950, &data) == OK) 800 { 801 data = (mode == 0) ? data & 0xffbf : data | 0x40; 802 Write_Word (dev->usb_handle, 0xe950, data); 803 } 804 805 DBG (DBG_FNC, "- Set_E950_Mode\n"); 806} 807 808static struct st_curve * 809Motor_Curve_Get (struct st_device *dev, SANE_Int motorcurve, 810 SANE_Int direction, SANE_Int itype) 811{ 812 struct st_curve *rst = NULL; 813 814 if (dev != NULL) 815 { 816 if ((dev->mtrsetting != NULL) && (motorcurve < dev->mtrsetting_count)) 817 { 818 struct st_motorcurve *mtc = dev->mtrsetting[motorcurve]; 819 820 if (mtc != NULL) 821 { 822 if ((mtc->curve != NULL) && (mtc->curve_count > 0)) 823 { 824 struct st_curve *crv; 825 SANE_Int a = 0; 826 827 while (a < mtc->curve_count) 828 { 829 /* get each curve */ 830 crv = mtc->curve[a]; 831 if (crv != NULL) 832 { 833 /* check direction and type */ 834 if ((crv->crv_speed == direction) 835 && (crv->crv_type == itype)) 836 { 837 /* found ! */ 838 rst = crv; 839 break; 840 } 841 } 842 a++; 843 } 844 } 845 } 846 } 847 } 848 849 return rst; 850} 851 852static SANE_Int 853Motor_Curve_Equal (struct st_device *dev, SANE_Int motorsetting, 854 SANE_Int direction, SANE_Int curve1, SANE_Int curve2) 855{ 856 /* compares two curves of the same direction 857 returns TRUE if both buffers are equal */ 858 859 SANE_Int rst = FALSE; 860 struct st_curve *crv1 = 861 Motor_Curve_Get (dev, motorsetting, direction, curve1); 862 struct st_curve *crv2 = 863 Motor_Curve_Get (dev, motorsetting, direction, curve2); 864 865 if ((crv1 != NULL) && (crv2 != NULL)) 866 { 867 if (crv1->step_count == crv2->step_count) 868 { 869 rst = TRUE; 870 871 if (crv1->step_count > 0) 872 { 873 SANE_Int a = 0; 874 875 while ((a < crv1->step_count) && (rst == TRUE)) 876 { 877 rst = (crv1->step[a] == crv2->step[a]) ? TRUE : FALSE; 878 a++; 879 } 880 } 881 } 882 } 883 884 return rst; 885} 886 887static struct st_motorcurve ** 888Motor_Curve_Parse (SANE_Int * mtc_count, SANE_Int * buffer) 889{ 890 /* this function parses motorcurve buffer to get all motor settings */ 891 struct st_motorcurve **rst = NULL; 892 893 *mtc_count = 0; 894 895 if (buffer != NULL) 896 { 897 /* phases: 898 -1 : null phase 899 0 : 900 -3 : initial config 901 */ 902 struct st_motorcurve *mtc = NULL; 903 SANE_Int phase; 904 905 phase = -1; 906 while (*buffer != -1) 907 { 908 if (*buffer == -2) 909 { 910 /* end of motorcurve */ 911 /* complete any opened phase */ 912 /* close phase */ 913 phase = -1; 914 } 915 else 916 { 917 /* step */ 918 if (phase == -1) 919 { 920 /* new motorcurve */ 921 phase = 0; 922 mtc = 923 (struct st_motorcurve *) 924 malloc (sizeof (struct st_motorcurve)); 925 if (mtc != NULL) 926 { 927 *mtc_count += 1; 928 rst = 929 realloc (rst, 930 sizeof (struct st_motorcurve **) * 931 *mtc_count); 932 if (rst != NULL) 933 { 934 rst[*mtc_count - 1] = mtc; 935 memset (mtc, 0, sizeof (struct st_motorcurve)); 936 phase = -3; /* initial config */ 937 } 938 else 939 { 940 /* memory error */ 941 *mtc_count = 0; 942 break; 943 } 944 } 945 else 946 break; /* some error */ 947 } 948 949 if (mtc != NULL) 950 { 951 switch (phase) 952 { 953 case -3: /* initial config */ 954 mtc->mri = *(buffer); 955 mtc->msi = *(buffer + 1); 956 mtc->skiplinecount = *(buffer + 2); 957 mtc->motorbackstep = *(buffer + 3); 958 buffer += 3; 959 960 phase = -4; 961 break; 962 963 case -4: 964 /**/ 965 { 966 /* create new step curve */ 967 struct st_curve *curve = 968 malloc (sizeof (struct st_curve)); 969 if (curve != NULL) 970 { 971 /* add to step curve list */ 972 mtc->curve = 973 (struct st_curve **) realloc (mtc->curve, 974 sizeof (struct 975 st_curve 976 **) * 977 (mtc-> 978 curve_count + 979 1)); 980 if (mtc->curve != NULL) 981 { 982 mtc->curve_count++; 983 mtc->curve[mtc->curve_count - 1] = curve; 984 985 memset (curve, 0, sizeof (struct st_curve)); 986 /* read crv speed and type */ 987 curve->crv_speed = *buffer; 988 curve->crv_type = *(buffer + 1); 989 buffer += 2; 990 991 /* get length of step buffer */ 992 while (*(buffer + curve->step_count) != 0) 993 curve->step_count++; 994 995 if (curve->step_count > 0) 996 { 997 /* allocate step buffer */ 998 curve->step = 999 (SANE_Int *) malloc (sizeof (SANE_Int) * 1000 curve->step_count); 1001 if (curve->step != NULL) 1002 { 1003 memcpy (curve->step, buffer, 1004 sizeof (SANE_Int) * 1005 curve->step_count); 1006 buffer += curve->step_count; 1007 } 1008 else 1009 curve->step_count = 0; 1010 } 1011 } 1012 else 1013 { 1014 mtc->curve_count = 0; 1015 free (curve); 1016 } 1017 } 1018 else 1019 break; 1020 } 1021 break; 1022 } 1023 } 1024 } 1025 buffer++; 1026 } 1027 } 1028 1029 return rst; 1030} 1031 1032static void 1033Motor_Curve_Free (struct st_motorcurve **motorcurves, SANE_Int * mtc_count) 1034{ 1035 if ((motorcurves != NULL) && (mtc_count != NULL)) 1036 { 1037 struct st_motorcurve *mtc; 1038 struct st_curve *curve; 1039 1040 while (*mtc_count > 0) 1041 { 1042 mtc = motorcurves[*mtc_count - 1]; 1043 if (mtc != NULL) 1044 { 1045 if (mtc->curve != NULL) 1046 { 1047 while (mtc->curve_count > 0) 1048 { 1049 curve = mtc->curve[mtc->curve_count - 1]; 1050 if (curve != NULL) 1051 { 1052 if (curve->step != NULL) 1053 free (curve->step); 1054 1055 free (curve); 1056 } 1057 mtc->curve_count--; 1058 } 1059 } 1060 free (mtc); 1061 } 1062 *mtc_count -= 1; 1063 } 1064 1065 free (motorcurves); 1066 } 1067} 1068 1069static SANE_Byte 1070RTS_Sensor_Type (USB_Handle usb_handle) 1071{ 1072 /* 1073 Returns sensor type 1074 01 = CCD 1075 00 = CIS 1076 */ 1077 1078 SANE_Int a, b, c; 1079 SANE_Byte rst; 1080 1081 DBG (DBG_FNC, "+ RTS_Sensor_Type:\n"); 1082 1083 a = b = c = 0; 1084 1085 /* Save data first */ 1086 Read_Word (usb_handle, 0xe950, &a); 1087 Read_Word (usb_handle, 0xe956, &b); 1088 1089 /* Enables GPIO 0xe950 writing directly 0x13ff */ 1090 Write_Word (usb_handle, 0xe950, 0x13ff); 1091 /* Sets GPIO 0xe956 writing 0xfcf0 */ 1092 Write_Word (usb_handle, 0xe956, 0xfcf0); 1093 /* Makes a sleep of 200 ms */ 1094 usleep (1000 * 200); 1095 /* Get GPIO 0xe968 */ 1096 Read_Word (usb_handle, 0xe968, &c); 1097 /* Restore data */ 1098 Write_Word (usb_handle, 0xe950, a); 1099 Write_Word (usb_handle, 0xe956, b); 1100 1101 rst = ((_B1 (c) & 1) == 0) ? CCD_SENSOR : CIS_SENSOR; 1102 1103 DBG (DBG_FNC, "- RTS_Sensor_Type: %s\n", 1104 (rst == CCD_SENSOR) ? "CCD" : "CIS"); 1105 1106 return rst; 1107} 1108 1109static void 1110Free_Scanmodes (struct st_device *dev) 1111{ 1112 DBG (DBG_FNC, "> Free_Scanmodes\n"); 1113 1114 if (dev->scanmodes != NULL) 1115 { 1116 if (dev->scanmodes_count > 0) 1117 { 1118 SANE_Int a; 1119 for (a = 0; a < dev->scanmodes_count; a++) 1120 if (dev->scanmodes[a] != NULL) 1121 free (dev->scanmodes[a]); 1122 } 1123 1124 free (dev->scanmodes); 1125 dev->scanmodes = NULL; 1126 } 1127 1128 dev->scanmodes_count = 0; 1129} 1130 1131static SANE_Int 1132Load_Scanmodes (struct st_device *dev) 1133{ 1134 SANE_Int rst = OK; 1135 SANE_Int a, b; 1136 struct st_scanmode reg, *mode; 1137 1138 DBG (DBG_FNC, "> Load_Scanmodes\n"); 1139 1140 if ((dev->scanmodes != NULL) || (dev->scanmodes_count > 0)) 1141 Free_Scanmodes (dev); 1142 1143 a = 0; 1144 while ((cfg_scanmode_get (dev->sensorcfg->type, a, ®) == OK) 1145 && (rst == OK)) 1146 { 1147 mode = (struct st_scanmode *) malloc (sizeof (struct st_scanmode)); 1148 if (mode != NULL) 1149 { 1150 memcpy (mode, ®, sizeof (struct st_scanmode)); 1151 1152 for (b = 0; b < 3; b++) 1153 { 1154 if (mode->mexpt[b] == 0) 1155 { 1156 mode->mexpt[b] = mode->ctpc; 1157 if (mode->multiexposure != 1) 1158 mode->expt[b] = mode->ctpc; 1159 } 1160 } 1161 1162 mode->ctpc = ((mode->ctpc + 1) * mode->multiexposure) - 1; 1163 1164 dev->scanmodes = 1165 (struct st_scanmode **) realloc (dev->scanmodes, 1166 (dev->scanmodes_count + 1167 1) * 1168 sizeof (struct st_scanmode **)); 1169 if (dev->scanmodes != NULL) 1170 { 1171 dev->scanmodes[dev->scanmodes_count] = mode; 1172 dev->scanmodes_count++; 1173 } 1174 else 1175 rst = ERROR; 1176 } 1177 else 1178 rst = ERROR; 1179 1180 a++; 1181 } 1182 1183 if (rst == ERROR) 1184 Free_Scanmodes (dev); 1185 1186 DBG (DBG_FNC, " -> Found %i scanmodes\n", dev->scanmodes_count); 1187 dbg_scanmodes (dev); 1188 1189 return rst; 1190} 1191 1192static void 1193Free_Config (struct st_device *dev) 1194{ 1195 DBG (DBG_FNC, "+ Free_Config\n"); 1196 1197 /* free buttons */ 1198 Free_Buttons (dev); 1199 1200 /* free motor general configuration */ 1201 Free_Motor (dev); 1202 1203 /* free sensor main configuration */ 1204 Free_Sensor (dev); 1205 1206 /* free ccd sensor timing tables */ 1207 Free_Timings (dev); 1208 1209 /* free motor curves */ 1210 Free_MotorCurves (dev); 1211 1212 /* free motor movements */ 1213 Free_Motormoves (dev); 1214 1215 /* free scan modes */ 1216 Free_Scanmodes (dev); 1217 1218 /* free constrains */ 1219 Free_Constrains (dev); 1220 1221 /* free chipset configuration */ 1222 Free_Chipset (dev); 1223 1224 DBG (DBG_FNC, "- Free_Config\n"); 1225} 1226 1227static void 1228Free_Chipset (struct st_device *dev) 1229{ 1230 DBG (DBG_FNC, "> Free_Chipset\n"); 1231 1232 if (dev->chipset != NULL) 1233 { 1234 if (dev->chipset->name != NULL) 1235 free (dev->chipset->name); 1236 1237 free (dev->chipset); 1238 dev->chipset = NULL; 1239 } 1240} 1241 1242static SANE_Int 1243Load_Chipset (struct st_device *dev) 1244{ 1245 SANE_Int rst = ERROR; 1246 1247 DBG (DBG_FNC, "> Load_Chipset\n"); 1248 1249 if (dev->chipset != NULL) 1250 Free_Chipset (dev); 1251 1252 dev->chipset = malloc (sizeof (struct st_chip)); 1253 if (dev->chipset != NULL) 1254 { 1255 SANE_Int model; 1256 1257 memset (dev->chipset, 0, sizeof (struct st_chip)); 1258 1259 /* get chipset model of selected scanner */ 1260 model = cfg_chipset_model_get (RTS_Debug->dev_model); 1261 1262 /* get configuration for selected chipset */ 1263 rst = cfg_chipset_get (model, dev->chipset); 1264 } 1265 1266 /* if rst == ERROR may be related to allocating space for chipset name */ 1267 1268 return rst; 1269} 1270 1271static SANE_Int 1272Load_Config (struct st_device *dev) 1273{ 1274 DBG (DBG_FNC, "+ Load_Config\n"); 1275 1276 /* load chipset configuration */ 1277 Load_Chipset (dev); 1278 1279 /* load scanner's buttons */ 1280 Load_Buttons (dev); 1281 1282 /* load scanner area constrains */ 1283 Load_Constrains (dev); 1284 1285 /* load motor general configuration */ 1286 Load_Motor (dev); 1287 1288 /* load sensor main configuration */ 1289 Load_Sensor (dev); 1290 1291 if (dev->sensorcfg->type == -1) 1292 /* get sensor from gpio */ 1293 dev->sensorcfg->type = RTS_Sensor_Type (dev->usb_handle); 1294 1295 /* load ccd sensor timing tables */ 1296 Load_Timings (dev); 1297 1298 /* load motor curves */ 1299 Load_MotorCurves (dev); 1300 1301 /* load motor movements */ 1302 Load_Motormoves (dev); 1303 1304 /* load scan modes */ 1305 Load_Scanmodes (dev); 1306 1307 /* deprecated */ 1308 if (dev->sensorcfg->type == CCD_SENSOR) 1309 /* ccd */ usbfile = 1310 (RTS_Debug->usbtype == USB20) ? T_RTINIFILE : T_USB1INIFILE; 1311 else /* cis */ 1312 usbfile = (RTS_Debug->usbtype == USB20) ? S_RTINIFILE : S_USB1INIFILE; 1313 1314 scantype = ST_NORMAL; 1315 1316 pwmlamplevel = get_value (SCAN_PARAM, PWMLAMPLEVEL, 1, usbfile); 1317 1318 arrangeline2 = get_value (SCAN_PARAM, ARRANGELINE, FIX_BY_HARD, usbfile); 1319 1320 shadingbase = get_value (TRUE_GRAY_PARAM, SHADINGBASE, 3, usbfile); 1321 shadingfact[0] = get_value (TRUE_GRAY_PARAM, SHADINGFACT1, 1, usbfile); 1322 shadingfact[1] = get_value (TRUE_GRAY_PARAM, SHADINGFACT2, 1, usbfile); 1323 shadingfact[2] = get_value (TRUE_GRAY_PARAM, SHADINGFACT3, 1, usbfile); 1324 1325 LoadImagingParams (dev, usbfile); 1326 1327 DBG (DBG_FNC, "- Load_Config\n"); 1328 1329 return OK; 1330} 1331 1332static SANE_Int 1333LoadImagingParams (struct st_device *dev, SANE_Int inifile) 1334{ 1335 DBG (DBG_FNC, "> LoadImagingParams(inifile='%i'):\n", inifile); 1336 1337 scan.startpos = get_value (SCAN_PARAM, STARTPOS, 0, inifile); 1338 scan.leftleading = get_value (SCAN_PARAM, LEFTLEADING, 0, inifile); 1339 arrangeline = get_value (SCAN_PARAM, ARRANGELINE, FIX_BY_HARD, inifile); 1340 compression = get_value (SCAN_PARAM, COMPRESSION, 0, inifile); 1341 1342 /* get default gain and offset values */ 1343 cfg_gainoffset_get (dev->sensorcfg->type, default_gain_offset); 1344 1345 linedarlampoff = get_value (CALI_PARAM, LINEDARLAMPOFF, 0, inifile); 1346 1347 pixeldarklevel = get_value (CALI_PARAM, PIXELDARKLEVEL, 0x00ffff, inifile); 1348 1349 binarythresholdh = get_value (PLATFORM, BINARYTHRESHOLDH, 0x80, inifile); 1350 binarythresholdl = get_value (PLATFORM, BINARYTHRESHOLDL, 0x7f, inifile); 1351 1352 return OK; 1353} 1354 1355static SANE_Int 1356Arrange_Colour (struct st_device *dev, SANE_Byte * buffer, 1357 SANE_Int buffer_size, SANE_Int * transferred) 1358{ 1359 /* 1360 05F0FA78 04EC00D8 /CALL to Assumed StdFunc2 from hpgt3970.04EC00D3 1361 05F0FA7C 05D10048 |Arg1 = 05D10048 1362 05F0FA80 0000F906 \Arg2 = 0000F906 1363 */ 1364 SANE_Int mydistance; 1365 SANE_Int Lines_Count; 1366 SANE_Int space; 1367 SANE_Int rst = OK; 1368 SANE_Int c; 1369 struct st_scanning *scn; 1370 1371 DBG (DBG_FNC, "> Arrange_Colour(*buffer, buffer_size=%i, *transferred)\n", 1372 buffer_size); 1373 1374 /* this is just to make code more legible */ 1375 scn = dev->scanning; 1376 1377 if (scn->imagebuffer == NULL) 1378 { 1379 if (dev->sensorcfg->type == CCD_SENSOR) 1380 mydistance = 1381 (dev->sensorcfg->line_distance * scan2.resolution_y) / 1382 dev->sensorcfg->resolution; 1383 else 1384 mydistance = 0; 1385 1386 /*aafa */ 1387 if (mydistance != 0) 1388 { 1389 scn->bfsize = 1390 (scn->arrange_hres == 1391 TRUE) ? scn->arrange_sensor_evenodd_dist : 0; 1392 scn->bfsize = (scn->bfsize + (mydistance * 2) + 1) * line_size; 1393 } 1394 else 1395 scn->bfsize = line_size * 2; 1396 1397 /*ab3c */ 1398 space = 1399 (((scn->bfsize / line_size) * bytesperline) > 1400 scn->bfsize) ? (scn->bfsize / line_size) * 1401 bytesperline : scn->bfsize; 1402 1403 scn->imagebuffer = (SANE_Byte *) malloc (space * sizeof (SANE_Byte)); 1404 if (scn->imagebuffer == NULL) 1405 return ERROR; 1406 1407 scn->imagepointer = scn->imagebuffer; 1408 1409 if (Read_Block (dev, scn->bfsize, scn->imagebuffer, transferred) != OK) 1410 return ERROR; 1411 1412 scn->arrange_orderchannel = FALSE; 1413 scn->channel_size = (scan2.depth == 8) ? 1 : 2; 1414 1415 /* Calculate channel displacements */ 1416 for (c = CL_RED; c <= CL_BLUE; c++) 1417 { 1418 if (mydistance == 0) 1419 { 1420 /*ab9b */ 1421 if (scn->arrange_hres == FALSE) 1422 { 1423 if ((((dev->sensorcfg->line_distance * scan2.resolution_y) * 1424 2) / dev->sensorcfg->resolution) == 1) 1425 scn->arrange_orderchannel = TRUE; 1426 1427 if (scn->arrange_orderchannel == TRUE) 1428 scn->desp[c] = 1429 ((dev->sensorcfg->rgb_order[c] / 2) * line_size) + 1430 (scn->channel_size * c); 1431 else 1432 scn->desp[c] = scn->channel_size * c; 1433 } 1434 } 1435 else 1436 { 1437 /*ac32 */ 1438 scn->desp[c] = 1439 (dev->sensorcfg->rgb_order[c] * (mydistance * line_size)) + 1440 (scn->channel_size * c); 1441 1442 if (scn->arrange_hres == TRUE) 1443 { 1444 scn->desp1[c] = scn->desp[c]; 1445 scn->desp2[c] = 1446 ((scn->channel_size * 3) + scn->desp[c]) + 1447 (scn->arrange_sensor_evenodd_dist * line_size); 1448 } 1449 } 1450 } 1451 1452 /*ace2 */ 1453 for (c = CL_RED; c <= CL_BLUE; c++) 1454 { 1455 if (scn->arrange_hres == TRUE) 1456 { 1457 scn->pColour2[c] = scn->imagebuffer + scn->desp2[c]; 1458 scn->pColour1[c] = scn->imagebuffer + scn->desp1[c]; 1459 } 1460 else 1461 scn->pColour[c] = scn->imagebuffer + scn->desp[c]; 1462 } 1463 } 1464 1465 /*ad91 */ 1466 Lines_Count = buffer_size / line_size; 1467 while (Lines_Count > 0) 1468 { 1469 if (scn->arrange_orderchannel == FALSE) 1470 { 1471 if (scn->arrange_hres == TRUE) 1472 Triplet_Colour_HRes (scn->pColour1[CL_RED], 1473 scn->pColour1[CL_GREEN], 1474 scn->pColour1[CL_BLUE], 1475 scn->pColour2[CL_RED], 1476 scn->pColour2[CL_GREEN], 1477 scn->pColour2[CL_BLUE], buffer, 1478 line_size / (scn->channel_size * 3)); 1479 else 1480 Triplet_Colour_LRes (line_size / (scn->channel_size * 3), buffer, 1481 scn->pColour[CL_RED], scn->pColour[CL_GREEN], 1482 scn->pColour[CL_BLUE]); 1483 } 1484 else 1485 Triplet_Colour_Order (dev, scn->pColour[CL_RED], 1486 scn->pColour[CL_GREEN], scn->pColour[CL_BLUE], 1487 buffer, line_size / (scn->channel_size * 3)); 1488 1489 scn->arrange_size -= bytesperline; 1490 if (scn->arrange_size < 0) 1491 v15bc--; 1492 1493 buffer += line_size; 1494 1495 Lines_Count--; 1496 if (Lines_Count == 0) 1497 { 1498 if ((scn->arrange_size | v15bc) == 0) 1499 return OK; 1500 } 1501 1502 if (Read_Block (dev, line_size, scn->imagepointer, transferred) == 1503 ERROR) 1504 return ERROR; 1505 1506 /* Update displacements */ 1507 for (c = CL_RED; c <= CL_BLUE; c++) 1508 { 1509 if (scn->arrange_hres == TRUE) 1510 { 1511 /*aeb7 */ 1512 scn->desp2[c] = (scn->desp2[c] + line_size) % scn->bfsize; 1513 scn->desp1[c] = (scn->desp1[c] + line_size) % scn->bfsize; 1514 1515 scn->pColour2[c] = scn->imagebuffer + scn->desp2[c]; 1516 scn->pColour1[c] = scn->imagebuffer + scn->desp1[c]; 1517 } 1518 else 1519 { 1520 /*af86 */ 1521 scn->desp[c] = (scn->desp[c] + line_size) % scn->bfsize; 1522 scn->pColour[c] = scn->imagebuffer + scn->desp[c]; 1523 } 1524 } 1525 1526 /*aff3 */ 1527 scn->imagepointer += line_size; 1528 if (scn->imagepointer >= (scn->imagebuffer + scn->bfsize)) 1529 scn->imagepointer = scn->imagebuffer; 1530 } 1531 1532 return rst; 1533} 1534 1535static SANE_Int 1536RTS_Scanner_SetParams (struct st_device *dev, struct params *param) 1537{ 1538 SANE_Int rst = ERROR; 1539 1540 DBG (DBG_FNC, "+ RTS_Scanner_SetParams:\n"); 1541 DBG (DBG_FNC, "-> param->resolution_x=%i\n", param->resolution_x); 1542 DBG (DBG_FNC, "-> param->resolution_y=%i\n", param->resolution_y); 1543 DBG (DBG_FNC, "-> param->left =%i\n", param->coords.left); 1544 DBG (DBG_FNC, "-> param->width =%i\n", param->coords.width); 1545 DBG (DBG_FNC, "-> param->top =%i\n", param->coords.top); 1546 DBG (DBG_FNC, "-> param->height =%i\n", param->coords.height); 1547 DBG (DBG_FNC, "-> param->colormode =%s\n", 1548 dbg_colour (param->colormode)); 1549 DBG (DBG_FNC, "-> param->scantype =%s\n", 1550 dbg_scantype (param->scantype)); 1551 DBG (DBG_FNC, "-> param->depth =%i\n", param->depth); 1552 DBG (DBG_FNC, "-> param->channel =%i\n", param->channel); 1553 1554 /* validate area size to scan */ 1555 if ((param->coords.width != 0) && (param->coords.height != 0)) 1556 { 1557 SANE_Byte mybuffer[1]; 1558 struct st_hwdconfig hwdcfg; 1559 1560 /* setting coordinates */ 1561 memcpy (&scan.coord, ¶m->coords, sizeof (struct st_coords)); 1562 1563 /* setting resolution */ 1564 scan.resolution_x = param->resolution_x; 1565 scan.resolution_y = param->resolution_y; 1566 1567 /* setting colormode and depth */ 1568 scan.colormode = param->colormode; 1569 scan.depth = (param->colormode == CM_LINEART) ? 8 : param->depth; 1570 1571 /* setting color channel for non color scans */ 1572 scan.channel = _B0 (param->channel); 1573 1574 arrangeline = FIX_BY_HARD; 1575 if ((scan.resolution_x == 2400) || ((scan.resolution_x == 4800))) 1576 { 1577 if (scan.colormode != CM_COLOR) 1578 { 1579 if (scan.colormode == CM_GRAY) 1580 { 1581 if (scan.channel == 3) 1582 arrangeline = FIX_BY_SOFT; 1583 } 1584 } 1585 else 1586 arrangeline = FIX_BY_SOFT; 1587 } 1588 1589 /* setting scan type */ 1590 if ((param->scantype > 0) && (param->scantype < 4)) 1591 scan.scantype = param->scantype; 1592 else 1593 scan.scantype = ST_NORMAL; 1594 1595 /* setting scanner lamp */ 1596 data_bitset (&dev->init_regs[0x146], 0x40, 1597 ((dev->sensorcfg->type == CIS_SENSOR) ? 0 : 1)); 1598 1599 /* turn on appropriate lamp */ 1600 if (scan.scantype == ST_NORMAL) 1601 Lamp_Status_Set (dev, NULL, TRUE, FLB_LAMP); 1602 else 1603 Lamp_Status_Set (dev, NULL, TRUE, TMA_LAMP); 1604 1605 mybuffer[0] = 0; 1606 if (RTS_IsExecuting (dev, mybuffer) == FALSE) 1607 RTS_WriteRegs (dev->usb_handle, dev->init_regs); 1608 1609 if (scan.depth == 16) 1610 compression = FALSE; 1611 1612 /* resetting low level config */ 1613 memset (&hwdcfg, 0, sizeof (struct st_hwdconfig)); 1614 1615 /* setting low level config */ 1616 hwdcfg.scantype = scan.scantype; 1617 hwdcfg.calibrate = mybuffer[0]; 1618 hwdcfg.arrangeline = arrangeline; /*1 */ 1619 hwdcfg.highresolution = (scan.resolution_x > 1200) ? TRUE : FALSE; 1620 hwdcfg.sensorevenodddistance = dev->sensorcfg->evenodd_distance; 1621 1622 SetScanParams (dev, dev->init_regs, &scan, &hwdcfg); 1623 1624 scan.shadinglength = 1625 (((scan.sensorresolution * 17) / 2) + 3) & 0xfffffffc; 1626 1627 rst = OK; 1628 } 1629 1630 DBG (DBG_FNC, "- RTS_Scanner_SetParams: %i\n", rst); 1631 1632 return rst; 1633} 1634 1635static SANE_Int 1636SetScanParams (struct st_device *dev, SANE_Byte * Regs, 1637 struct st_scanparams *scancfg, struct st_hwdconfig *hwdcfg) 1638{ 1639 struct st_coords mycoords; 1640 SANE_Int mycolormode; 1641 SANE_Int myvalue; 1642 SANE_Int mymode; 1643 SANE_Int channel_size; 1644 SANE_Int channel_count; 1645 SANE_Int dots_per_block; 1646 SANE_Int aditional_dots; 1647 1648 DBG (DBG_FNC, "+ SetScanParams:\n"); 1649 dbg_ScanParams (scancfg); 1650 dbg_hwdcfg (hwdcfg); 1651 1652 memset (&mycoords, 0, sizeof (struct st_coords)); 1653 /* Copy scancfg to scan2 */ 1654 memcpy (&scan2, scancfg, sizeof (struct st_scanparams)); 1655 1656 mycolormode = scancfg->colormode; 1657 myvalue = scancfg->colormode; 1658 scantype = hwdcfg->scantype; 1659 1660 if (scancfg->colormode == CM_LINEART) 1661 scan2.depth = 8; 1662 1663 if ((scancfg->colormode != CM_COLOR) && (scancfg->channel == 3)) /*channel = 0x00 */ 1664 { 1665 if (scancfg->colormode == CM_GRAY) 1666 { 1667 mycolormode = (hwdcfg->arrangeline != FIX_BY_SOFT) ? 3 : CM_COLOR; 1668 } 1669 else 1670 mycolormode = 3; 1671 myvalue = mycolormode; 1672 } 1673 1674 dev->Resize->resolution_x = scancfg->resolution_x; 1675 dev->Resize->resolution_y = scancfg->resolution_y; 1676 1677 mymode = RTS_GetScanmode (dev, hwdcfg->scantype, myvalue, scancfg->resolution_x); /*0x0b */ 1678 if (mymode == -1) 1679 { 1680 /* Non supported resolution. We will resize image after scanning */ 1681 SANE_Int fitres; 1682 1683 fitres = 1684 Scanmode_fitres (dev, hwdcfg->scantype, scancfg->colormode, 1685 scancfg->resolution_x); 1686 if (fitres != -1) 1687 { 1688 /* supported resolution found */ 1689 dev->Resize->type = RSZ_DECREASE; 1690 } 1691 else 1692 { 1693 dev->Resize->type = RSZ_INCREASE; 1694 fitres = 1695 Scanmode_maxres (dev, hwdcfg->scantype, scancfg->colormode); 1696 } 1697 1698 scan2.resolution_x = fitres; 1699 scan2.resolution_y = fitres; 1700 1701 mymode = 1702 RTS_GetScanmode (dev, hwdcfg->scantype, myvalue, scan2.resolution_x); 1703 if (mymode == -1) 1704 return ERROR; 1705 1706 imageheight = scancfg->coord.height; 1707 dev->Resize->towidth = scancfg->coord.width; 1708 1709 /* Calculate coords for new resolution */ 1710 mycoords.left = 1711 (scan2.resolution_x * scancfg->coord.left) / 1712 dev->Resize->resolution_x; 1713 mycoords.width = 1714 (scan2.resolution_x * scancfg->coord.width) / 1715 dev->Resize->resolution_x; 1716 mycoords.top = 1717 (scan2.resolution_y * scancfg->coord.top) / dev->Resize->resolution_y; 1718 mycoords.height = 1719 ((scan2.resolution_y * scancfg->coord.height) / 1720 dev->Resize->resolution_y) + 2; 1721 1722 switch (scan2.colormode) 1723 { 1724 case CM_GRAY: 1725 if ((dev->scanmodes[mymode]->samplerate == PIXEL_RATE) 1726 && (mycolormode != 3)) 1727 dev->Resize->towidth *= 2; 1728 1729 channel_size = (scan2.depth == 8) ? 1 : 2; 1730 dev->Resize->mode = (scan2.depth == 8) ? RSZ_GRAYL : RSZ_GRAYH; 1731 dev->Resize->bytesperline = dev->Resize->towidth * channel_size; 1732 break; 1733 case CM_LINEART: 1734 if (dev->scanmodes[mymode]->samplerate == PIXEL_RATE) 1735 dev->Resize->towidth *= 2; 1736 1737 dev->Resize->mode = RSZ_LINEART; 1738 dev->Resize->bytesperline = (dev->Resize->towidth + 7) / 8; 1739 break; 1740 default: /*CM_COLOR */ 1741 channel_count = 3; 1742 channel_size = (scan2.depth == 8) ? 1 : 2; 1743 dev->Resize->mode = (scan2.depth == 8) ? RSZ_COLOURL : RSZ_COLOURH; 1744 dev->Resize->bytesperline = 1745 scancfg->coord.width * (channel_count * channel_size); 1746 break; 1747 } 1748 } 1749 else 1750 { 1751 /* Supported scanmode */ 1752 dev->Resize->type = RSZ_NONE; 1753 scan2.resolution_x = scancfg->resolution_x; 1754 scan2.resolution_y = scancfg->resolution_y; 1755 mycoords.left = scancfg->coord.left; 1756 mycoords.top = scancfg->coord.top; 1757 mycoords.width = scancfg->coord.width; 1758 mycoords.height = scancfg->coord.height; 1759 } 1760 1761 scancfg->timing = dev->scanmodes[mymode]->timing; 1762 1763 scan2.sensorresolution = dev->timings[scancfg->timing]->sensorresolution; 1764 if ((scantype > 0) && (scantype < 5)) 1765 scan2.shadinglength = 1766 (((scan2.sensorresolution * 17) / 2) + 3) & 0xfffffffc; 1767 1768 scancfg->sensorresolution = scan2.sensorresolution; 1769 scancfg->shadinglength = scan2.shadinglength; 1770 1771 dev->scanning->arrange_compression = ((mycolormode != CM_LINEART) 1772 && (scan2.depth <= 1773 8)) ? hwdcfg->compression : FALSE; 1774 1775 if ((arrangeline2 == FIX_BY_HARD) || (mycolormode == CM_LINEART)) 1776 arrangeline2 = mycolormode; /*¿? */ 1777 else if ((mycolormode == CM_GRAY) && (hwdcfg->highresolution == FALSE)) 1778 arrangeline2 = 0; 1779 1780 if (hwdcfg->highresolution == FALSE) 1781 { 1782 /* resolution < 1200 dpi */ 1783 dev->scanning->arrange_hres = FALSE; 1784 dev->scanning->arrange_sensor_evenodd_dist = 0; 1785 } 1786 else 1787 { 1788 /* resolution > 1200 dpi */ 1789 dev->scanning->arrange_hres = TRUE; 1790 dev->scanning->arrange_sensor_evenodd_dist = 1791 hwdcfg->sensorevenodddistance; 1792 } 1793 1794 /* with must be adjusted to fit in the dots count per block */ 1795 aditional_dots = 0; 1796 if (mycolormode != CM_LINEART) 1797 { 1798 dots_per_block = ((scan2.resolution_x > 2400) 1799 && (scancfg->samplerate == PIXEL_RATE)) ? 8 : 4; 1800 1801 /* fit width */ 1802 if ((mycoords.width % dots_per_block) != 0) 1803 { 1804 aditional_dots = dots_per_block - (mycoords.width % dots_per_block); 1805 mycoords.width += aditional_dots; 1806 } 1807 } 1808 else 1809 { 1810 /* Lineart */ 1811 dots_per_block = 32 - (mycoords.width & 0x1f); 1812 if (dots_per_block < 32) 1813 { 1814 mycoords.width += dots_per_block; 1815 aditional_dots = (dots_per_block / 8); 1816 } 1817 } 1818 1819 DBG (DBG_FNC, " -> dots_per_block: %i\n", dots_per_block); 1820 DBG (DBG_FNC, " -> aditional_dots: %i\n", aditional_dots); 1821 1822 if (mycolormode == CM_LINEART) 1823 { 1824 bytesperline = 1825 (dev->scanmodes[mymode]->samplerate == 1826 PIXEL_RATE) ? mycoords.width / 4 : mycoords.width / 8; 1827 imagewidth3 = bytesperline; 1828 lineart_width = bytesperline * 8; 1829 line_size = bytesperline - aditional_dots; 1830 dev->Resize->fromwidth = line_size * 8; 1831 } 1832 else 1833 { 1834 /*4510 */ 1835 switch (mycolormode) 1836 { 1837 case CM_COLOR: 1838 channel_count = 3; 1839 break; 1840 case 3: 1841 channel_count = 1; 1842 break; 1843 case CM_GRAY: 1844 channel_count = (dev->scanmodes[mymode]->samplerate == PIXEL_RATE) ? 2 : 1; /*1 */ 1845 break; 1846 } 1847 1848 channel_size = (scan2.depth == 8) ? 1 : 2; 1849 bytesperline = mycoords.width * (channel_count * channel_size); 1850 imagewidth3 = bytesperline / channel_count; 1851 lineart_width = imagewidth3 / channel_size; 1852 line_size = 1853 bytesperline - (aditional_dots * (channel_count * channel_size)); 1854 dev->Resize->fromwidth = line_size / (channel_count * channel_size); 1855 } 1856 1857 imagesize = mycoords.height * bytesperline; 1858 v15b4 = 0; 1859 dev->scanning->arrange_size = imagesize; 1860 v15bc = 0; 1861 1862 /* set resolution ratio */ 1863 data_bitset (&Regs[0xc0], 0x1f, 1864 scancfg->sensorresolution / scancfg->resolution_x); 1865 1866 scancfg->coord.left = mycoords.left; 1867 scancfg->coord.top = mycoords.top; 1868 scancfg->coord.width = mycoords.width; 1869 scancfg->coord.height = mycoords.height; 1870 scancfg->resolution_x = scan2.resolution_x; 1871 scancfg->resolution_y = scan2.resolution_y; 1872 1873 myvalue = 1874 (dev->Resize->type == RSZ_NONE) ? line_size : dev->Resize->bytesperline; 1875 scancfg->bytesperline = bytesperline; 1876 1877 scancfg->v157c = myvalue; 1878 1879 if (scan.colormode != CM_COLOR) 1880 { 1881 if (mycolormode == CM_COLOR) 1882 scancfg->v157c = (scancfg->v157c / 3); 1883 } 1884 1885 if (scan.colormode == CM_LINEART) 1886 { 1887 if (mycolormode == 3) 1888 { 1889 scancfg->v157c = (scancfg->v157c + 7) / 8; 1890 scancfg->bytesperline = (scancfg->bytesperline + 7) / 8; 1891 } 1892 } 1893 1894 DBG (DBG_FNC, "- SetScanParams:\n"); 1895 1896 return OK; 1897} 1898 1899static SANE_Int 1900GainOffset_Counter_Save (struct st_device *dev, SANE_Byte data) 1901{ 1902 SANE_Int rst = OK; 1903 1904 DBG (DBG_FNC, "> GainOffset_Counter_Save(data=%i):\n", data); 1905 1906 /* check if chipset supports accessing eeprom */ 1907 if ((dev->chipset->capabilities & CAP_EEPROM) != 0) 1908 { 1909 data = min (data, 0x0f); 1910 rst = RTS_EEPROM_WriteByte (dev->usb_handle, 0x0077, data); 1911 } 1912 1913 return rst; 1914} 1915 1916static SANE_Int 1917GainOffset_Counter_Inc (struct st_device *dev, SANE_Int * arg1) 1918{ 1919 SANE_Byte count; 1920 SANE_Int rst; 1921 1922 DBG (DBG_FNC, "+ GainOffset_Counter_Inc:\n"); 1923 1924 /* check if chipset supports accessing eeprom */ 1925 if ((dev->chipset->capabilities & CAP_EEPROM) != 0) 1926 { 1927 count = GainOffset_Counter_Load (dev); 1928 if ((count >= 0x0f) || (GainOffset_Get (dev) != OK)) 1929 { 1930 offset[CL_BLUE] = offset[CL_GREEN] = offset[CL_RED] = 0; 1931 gain[CL_BLUE] = gain[CL_GREEN] = gain[CL_RED] = 0; 1932 count = 0; 1933 } 1934 else 1935 { 1936 count++; 1937 if (arg1 != NULL) 1938 *arg1 = 1; 1939 } 1940 1941 rst = GainOffset_Counter_Save (dev, count); 1942 } 1943 else 1944 rst = OK; 1945 1946 DBG (DBG_FNC, "- GainOffset_Counter_Inc: %i\n", rst); 1947 1948 return rst; 1949} 1950 1951static SANE_Int 1952GainOffset_Get (struct st_device *dev) 1953{ 1954 SANE_Int a, data, rst; 1955 SANE_Byte checksum; 1956 1957 DBG (DBG_FNC, "+ GainOffset_Get:\n"); 1958 1959 checksum = 0; 1960 1961 /* check if chipset supports accessing eeprom */ 1962 if ((dev->chipset->capabilities & CAP_EEPROM) != 0) 1963 { 1964 /* get current checksum */ 1965 if (RTS_EEPROM_ReadByte (dev->usb_handle, 0x76, &checksum) == OK) 1966 { 1967 rst = OK; 1968 1969 /* read gain and offset values from EEPROM */ 1970 for (a = CL_RED; a <= CL_BLUE; a++) 1971 { 1972 if (RTS_EEPROM_ReadWord (dev->usb_handle, 0x70 + (2 * a), &data) 1973 == ERROR) 1974 { 1975 rst = ERROR; 1976 break; 1977 } 1978 else 1979 offset[a] = data; 1980 } 1981 1982 /* check checksum */ 1983 checksum = 1984 _B0 (checksum + offset[CL_GREEN] + offset[CL_BLUE] + 1985 offset[CL_RED]); 1986 } 1987 else 1988 rst = ERROR; 1989 } 1990 else 1991 rst = ERROR; 1992 1993 /* extract gain and offset values */ 1994 if ((rst == OK) && (checksum == 0x5b)) 1995 { 1996 for (a = CL_RED; a <= CL_BLUE; a++) 1997 { 1998 gain[a] = (offset[a] >> 9) & 0x1f; 1999 offset[a] &= 0x01ff; 2000 } 2001 } 2002 else 2003 { 2004 /* null values, let's reset them */ 2005 for (a = CL_RED; a <= CL_BLUE; a++) 2006 { 2007 gain[a] = 0; 2008 offset[a] = 0; 2009 } 2010 2011 rst = ERROR; 2012 } 2013 2014 DBG (DBG_FNC, 2015 "-> Preview gainR=%i, gainG=%i, gainB=%i, offsetR=%i, offsetG=%i, offsetB=%i\n", 2016 gain[CL_RED], gain[CL_GREEN], gain[CL_BLUE], offset[CL_RED], 2017 offset[CL_GREEN], offset[CL_BLUE]); 2018 2019 DBG (DBG_FNC, "- GainOffset_Get: %i\n", rst); 2020 2021 return rst; 2022} 2023 2024static SANE_Int 2025Scanmode_maxres (struct st_device *dev, SANE_Int scantype, SANE_Int colormode) 2026{ 2027 /* returns position in scanmodes table where data fits with given arguments */ 2028 SANE_Int rst = 0; 2029 SANE_Int a; 2030 struct st_scanmode *reg; 2031 2032 for (a = 0; a < dev->scanmodes_count; a++) 2033 { 2034 reg = dev->scanmodes[a]; 2035 if (reg != NULL) 2036 { 2037 if ((reg->scantype == scantype) && (reg->colormode == colormode)) 2038 rst = max (rst, reg->resolution); /* found ! */ 2039 } 2040 } 2041 2042 if (rst == 0) 2043 { 2044 /* There isn't any mode for these arguments. 2045 Most devices doesn't support specific setup to scan in lineart mode 2046 so they use gray colormode. Lets check this case */ 2047 if (colormode == CM_LINEART) 2048 rst = Scanmode_maxres (dev, scantype, CM_GRAY); 2049 } 2050 2051 DBG (DBG_FNC, "> Scanmode_maxres(scantype=%s, colormode=%s): %i\n", 2052 dbg_scantype (scantype), dbg_colour (colormode), rst); 2053 2054 return rst; 2055} 2056 2057static SANE_Int 2058Scanmode_minres (struct st_device *dev, SANE_Int scantype, SANE_Int colormode) 2059{ 2060 /* returns position in scanmodes table where data fits with given arguments */ 2061 SANE_Int rst, a; 2062 struct st_scanmode *reg; 2063 2064 rst = Scanmode_maxres (dev, scantype, colormode); 2065 2066 for (a = 0; a < dev->scanmodes_count; a++) 2067 { 2068 reg = dev->scanmodes[a]; 2069 if (reg != NULL) 2070 { 2071 if ((reg->scantype == scantype) && (reg->colormode == colormode)) 2072 rst = min (rst, reg->resolution); /* found ! */ 2073 } 2074 } 2075 2076 if (rst == 0) 2077 { 2078 /* There isn't any mode for these arguments. 2079 Most devices doesn't support specific setup to scan in lineart mode 2080 so they use gray colormode. Lets check this case */ 2081 if (colormode == CM_LINEART) 2082 rst = Scanmode_minres (dev, scantype, CM_GRAY); 2083 } 2084 2085 DBG (DBG_FNC, "> Scanmode_minres(scantype=%s, colormode=%s): %i\n", 2086 dbg_scantype (scantype), dbg_colour (colormode), rst); 2087 2088 return rst; 2089} 2090 2091static SANE_Int 2092Scanmode_fitres (struct st_device *dev, SANE_Int scantype, SANE_Int colormode, 2093 SANE_Int resolution) 2094{ 2095 /* returns a supported resolution */ 2096 SANE_Int rst; 2097 SANE_Int a, nullres; 2098 struct st_scanmode *reg; 2099 2100 nullres = Scanmode_maxres (dev, scantype, colormode) + 1; 2101 rst = nullres; 2102 2103 for (a = 0; a < dev->scanmodes_count; a++) 2104 { 2105 reg = dev->scanmodes[a]; 2106 if (reg != NULL) 2107 { 2108 if ((reg->scantype == scantype) && (reg->colormode == colormode)) 2109 { 2110 if ((reg->resolution < rst) && (resolution <= reg->resolution)) 2111 rst = reg->resolution; 2112 } 2113 } 2114 } 2115 2116 if (rst == nullres) 2117 { 2118 /* There isn't any mode for these arguments. 2119 Most devices doesn't support specific setup to scan in lineart mode 2120 so they use gray colormode. Lets check this case */ 2121 if (colormode != CM_LINEART) 2122 { 2123 /* at this point, given resolution is bigger than maximum supported resolution */ 2124 rst = -1; 2125 } 2126 else 2127 rst = Scanmode_minres (dev, scantype, CM_GRAY); 2128 } 2129 2130 DBG (DBG_FNC, 2131 "> Scanmode_fitres(scantype=%s, colormode=%s, resolution=%i): %i\n", 2132 dbg_scantype (scantype), dbg_colour (colormode), resolution, rst); 2133 2134 return rst; 2135} 2136 2137static SANE_Int 2138RTS_GetScanmode (struct st_device *dev, SANE_Int scantype, SANE_Int colormode, 2139 SANE_Int resolution) 2140{ 2141 /* returns position in scanmodes table where data fits with given arguments */ 2142 SANE_Int rst = -1; 2143 SANE_Int a; 2144 struct st_scanmode *reg; 2145 2146 for (a = 0; a < dev->scanmodes_count; a++) 2147 { 2148 reg = dev->scanmodes[a]; 2149 if (reg != NULL) 2150 { 2151 if ((reg->scantype == scantype) && (reg->colormode == colormode) 2152 && (reg->resolution == resolution)) 2153 { 2154 /* found ! */ 2155 rst = a; 2156 break; 2157 } 2158 } 2159 } 2160 2161 if (rst == -1) 2162 { 2163 /* There isn't any mode for these arguments. 2164 May be given resolution isn't supported by chipset. 2165 Most devices doesn't support specific setup to scan in lineart mode 2166 so they use gray colormode. Lets check this case */ 2167 if ((colormode == CM_LINEART) || (colormode == 3)) 2168 rst = RTS_GetScanmode (dev, scantype, CM_GRAY, resolution); 2169 } 2170 2171 DBG (DBG_FNC, 2172 "> RTS_GetScanmode(scantype=%s, colormode=%s, resolution=%i): %i\n", 2173 dbg_scantype (scantype), dbg_colour (colormode), resolution, rst); 2174 2175 return rst; 2176} 2177 2178static void 2179Free_Motor (struct st_device *dev) 2180{ 2181 /* this function releases space for stepper motor */ 2182 2183 DBG (DBG_FNC, "> Free_Motor\n"); 2184 2185 if (dev->motorcfg != NULL) 2186 { 2187 free (dev->motorcfg); 2188 dev->motorcfg = NULL; 2189 } 2190} 2191 2192static SANE_Int 2193Load_Motor (struct st_device *dev) 2194{ 2195 /* this function loads general configuration for motor */ 2196 2197 SANE_Int rst = ERROR; 2198 2199 DBG (DBG_FNC, "> Load_Motor\n"); 2200 2201 if (dev->motorcfg != NULL) 2202 Free_Motor (dev); 2203 2204 dev->motorcfg = malloc (sizeof (struct st_motorcfg)); 2205 if (dev->motorcfg != NULL) 2206 { 2207 rst = cfg_motor_get (dev->motorcfg); 2208 dbg_motorcfg (dev->motorcfg); 2209 } 2210 2211 return rst; 2212} 2213 2214static void 2215Free_Sensor (struct st_device *dev) 2216{ 2217 /* this function releases space for ccd sensor */ 2218 2219 DBG (DBG_FNC, "> Free_Sensor\n"); 2220 2221 if (dev->sensorcfg != NULL) 2222 { 2223 free (dev->sensorcfg); 2224 dev->sensorcfg = NULL; 2225 } 2226} 2227 2228static void 2229Free_Buttons (struct st_device *dev) 2230{ 2231 /* this function releases space for buttons */ 2232 2233 DBG (DBG_FNC, "> Free_Buttons\n"); 2234 2235 if (dev->buttons != NULL) 2236 { 2237 free (dev->buttons); 2238 dev->buttons = NULL; 2239 } 2240} 2241 2242static SANE_Int 2243Load_Buttons (struct st_device *dev) 2244{ 2245 /* this function loads configuration for ccd sensor */ 2246 2247 SANE_Int rst = ERROR; 2248 2249 DBG (DBG_FNC, "> Load_Buttons\n"); 2250 2251 if (dev->buttons != NULL) 2252 Free_Buttons (dev); 2253 2254 dev->buttons = malloc (sizeof (struct st_buttons)); 2255 if (dev->buttons != NULL) 2256 { 2257 rst = cfg_buttons_get (dev->buttons); 2258 dbg_buttons (dev->buttons); 2259 } 2260 2261 return rst; 2262} 2263 2264static SANE_Int 2265Load_Sensor (struct st_device *dev) 2266{ 2267 /* this function loads configuration for ccd sensor */ 2268 2269 SANE_Int rst = ERROR; 2270 2271 DBG (DBG_FNC, "> Load_Sensor\n"); 2272 2273 if (dev->sensorcfg != NULL) 2274 Free_Sensor (dev); 2275 2276 dev->sensorcfg = malloc (sizeof (struct st_sensorcfg)); 2277 if (dev->sensorcfg != NULL) 2278 { 2279 rst = cfg_sensor_get (dev->sensorcfg); 2280 dbg_sensor (dev->sensorcfg); 2281 } 2282 2283 return rst; 2284} 2285 2286static void 2287Free_Timings (struct st_device *dev) 2288{ 2289 /* this function frees all ccd sensor timing tables */ 2290 DBG (DBG_FNC, "> Free_Timings\n"); 2291 2292 if (dev->timings != NULL) 2293 { 2294 if (dev->timings_count > 0) 2295 { 2296 SANE_Int a; 2297 for (a = 0; a < dev->timings_count; a++) 2298 if (dev->timings[a] != NULL) 2299 free (dev->timings[a]); 2300 2301 dev->timings_count = 0; 2302 } 2303 2304 free (dev->timings); 2305 dev->timings = NULL; 2306 } 2307} 2308 2309static SANE_Int 2310Load_Timings (struct st_device *dev) 2311{ 2312 SANE_Int rst = OK; 2313 SANE_Int a; 2314 struct st_timing reg, *tmg; 2315 2316 DBG (DBG_FNC, "> Load_Timings\n"); 2317 2318 if (dev->timings != NULL) 2319 Free_Timings (dev); 2320 2321 a = 0; 2322 2323 while ((cfg_timing_get (dev->sensorcfg->type, a, ®) == OK) 2324 && (rst == OK)) 2325 { 2326 tmg = (struct st_timing *) malloc (sizeof (struct st_timing)); 2327 if (tmg != NULL) 2328 { 2329 memcpy (tmg, ®, sizeof (struct st_timing)); 2330 2331 dev->timings_count++; 2332 dev->timings = 2333 (struct st_timing **) realloc (dev->timings, 2334 sizeof (struct st_timing **) * 2335 dev->timings_count); 2336 if (dev->timings == NULL) 2337 { 2338 rst = ERROR; 2339 dev->timings_count = 0; 2340 } 2341 else 2342 dev->timings[dev->timings_count - 1] = tmg; 2343 } 2344 else 2345 rst = ERROR; 2346 2347 a++; 2348 } 2349 2350 if (rst == ERROR) 2351 Free_Timings (dev); 2352 2353 DBG (DBG_FNC, " -> Found %i timing registers\n", dev->timings_count); 2354 2355 return rst; 2356} 2357 2358static SANE_Int 2359IsScannerLinked (struct st_device *dev) 2360{ 2361 SANE_Int var2; 2362 SANE_Byte lamp; 2363 2364 DBG (DBG_FNC, "+ IsScannerLinked:\n"); 2365 2366 Read_FE3E (dev, &v1619); 2367 Init_USBData (dev); 2368 scan.scantype = ST_NORMAL; 2369 2370 RTS_WaitInitEnd (dev, 0x30000); 2371 2372 lamp = FLB_LAMP; 2373 2374 /* Comprobar si es la primera conexión con el escaner */ 2375 if (Read_Word (dev->usb_handle, 0xe829, &var2) == OK) 2376 { 2377 SANE_Int firstconnection; 2378 2379#ifdef STANDALONE 2380 firstconnection = TRUE; 2381#else 2382 firstconnection = (var2 == 0) ? TRUE : FALSE; 2383#endif 2384 2385 if (firstconnection == TRUE) 2386 { 2387 /* primera conexión */ 2388 SANE_Byte flb_lamp, tma_lamp; 2389 2390 flb_lamp = 0; 2391 tma_lamp = 0; 2392 Lamp_Status_Get (dev, &flb_lamp, &tma_lamp); 2393 2394 if ((flb_lamp == 0) && (tma_lamp != 0)) 2395 lamp = TMA_LAMP; 2396 2397 /*Clear GainOffset count */ 2398 GainOffset_Clear (dev); 2399 GainOffset_Counter_Save (dev, 0); 2400 2401 /* Clear AutoRef count */ 2402 Refs_Counter_Save (dev, 0); 2403 2404 Buttons_Enable (dev); 2405 Lamp_Status_Timer_Set (dev, 13); 2406 } 2407 else 2408 lamp = (_B0 (var2) == 0) ? FLB_LAMP : TMA_LAMP; 2409 } 2410 2411 if (RTS_Warm_Reset (dev) != OK) 2412 return ERROR; 2413 2414 Head_ParkHome (dev, TRUE, dev->motorcfg->parkhomemotormove); 2415 2416 Lamp_Status_Timer_Set (dev, 13); 2417 2418 /* Use fixed pwm? */ 2419 if (RTS_Debug->use_fixed_pwm != FALSE) 2420 { 2421 Lamp_PWM_Save (dev, cfg_fixedpwm_get (dev->sensorcfg->type, ST_NORMAL)); 2422 /* Lets enable using fixed pwm */ 2423 Lamp_PWM_SaveStatus (dev, TRUE); 2424 } 2425 2426 Lamp_PWM_Setup (dev, lamp); 2427 2428 DBG (DBG_FNC, "- IsScannerLinked:\n"); 2429 2430 return OK; 2431} 2432 2433static SANE_Int 2434Lamp_PWM_SaveStatus (struct st_device *dev, SANE_Byte status) 2435{ 2436 SANE_Byte mypwm; 2437 SANE_Int rst = OK; 2438 2439 DBG (DBG_FNC, "+ Lamp_PWM_SaveStatus(status=%i):\n", status); 2440 2441 /* check if chipset supports accessing eeprom */ 2442 if ((dev->chipset->capabilities & CAP_EEPROM) != 0) 2443 { 2444 rst = ERROR; 2445 2446 if (RTS_EEPROM_ReadByte (dev->usb_handle, 0x007b, &mypwm) == OK) 2447 { 2448 mypwm = (status == FALSE) ? mypwm & 0x7f : mypwm | 0x80; 2449 2450 if (RTS_EEPROM_WriteByte (dev->usb_handle, 0x007b, mypwm) == OK) 2451 rst = OK; 2452 } 2453 } 2454 2455 DBG (DBG_FNC, "- Lamp_PWM_SaveStatus: %i\n", rst); 2456 2457 return rst; 2458} 2459 2460static SANE_Int 2461Lamp_PWM_Save (struct st_device *dev, SANE_Int fixedpwm) 2462{ 2463 SANE_Int rst; 2464 2465 DBG (DBG_FNC, "+ Lamp_PWM_Save(fixedpwm=%i):\n", fixedpwm); 2466 2467 /* check if chipset supports accessing eeprom */ 2468 if ((dev->chipset->capabilities & CAP_EEPROM) != 0) 2469 rst = 2470 RTS_EEPROM_WriteByte (dev->usb_handle, 0x7b, ((fixedpwm << 2) | 0x80)); 2471 else 2472 rst = OK; 2473 2474 DBG (DBG_FNC, "- Lamp_PWM_Save: %i\n", rst); 2475 2476 return rst; 2477} 2478 2479static SANE_Int 2480Lamp_PWM_Setup (struct st_device *dev, SANE_Int lamp) 2481{ 2482 SANE_Int rst = OK; 2483 2484 DBG (DBG_FNC, "+ Lamp_PWM_Setup(lamp=%s):\n", 2485 (lamp == FLB_LAMP) ? "FLB_LAMP" : "TMA_LAMP"); 2486 2487 if (Lamp_PWM_use (dev, 1) == OK) 2488 { 2489 SANE_Int fixedpwm, currentpwd; 2490 2491 currentpwd = 0; 2492 fixedpwm = 2493 cfg_fixedpwm_get (dev->sensorcfg->type, 2494 (lamp == FLB_LAMP) ? ST_NORMAL : ST_TA); 2495 2496 if (Lamp_PWM_DutyCycle_Get (dev, ¤tpwd) == OK) 2497 { 2498 /* set duty cycle if current one is different */ 2499 if (currentpwd != fixedpwm) 2500 rst = Lamp_PWM_DutyCycle_Set (dev, fixedpwm); 2501 } 2502 else 2503 rst = Lamp_PWM_DutyCycle_Set (dev, fixedpwm); 2504 } 2505 2506 DBG (DBG_FNC, "- Lamp_PWM_Setup: %i\n", rst); 2507 2508 return rst; 2509} 2510 2511static SANE_Int 2512Lamp_PWM_DutyCycle_Get (struct st_device *dev, SANE_Int * data) 2513{ 2514 SANE_Byte a; 2515 SANE_Int rst = ERROR; 2516 2517 DBG (DBG_FNC, "+ Lamp_PWM_DutyCycle_Get:\n"); 2518 2519 if (Read_Byte (dev->usb_handle, 0xe948, &a) == OK) 2520 { 2521 *data = a & 0x3f; 2522 rst = OK; 2523 } 2524 2525 DBG (DBG_FNC, "- Lamp_PWM_DutyCycle_Get = %i: %i\n", *data, rst); 2526 2527 return rst; 2528} 2529 2530static SANE_Int 2531Lamp_PWM_DutyCycle_Set (struct st_device *dev, SANE_Int duty_cycle) 2532{ 2533 SANE_Byte *Regs; 2534 SANE_Int rst; 2535 2536 DBG (DBG_FNC, "+ Lamp_PWM_DutyCycle_Set(duty_cycle=%i):\n", duty_cycle); 2537 2538 rst = ERROR; 2539 2540 Regs = (SANE_Byte *) malloc (RT_BUFFER_LEN * sizeof (SANE_Byte)); 2541 if (Regs != NULL) 2542 { 2543 if (RTS_ReadRegs (dev->usb_handle, Regs) == OK) 2544 { 2545 data_bitset (&Regs[0x148], 0x3f, duty_cycle); 2546 2547 if (pwmlamplevel == 0) 2548 { 2549 data_bitset (&Regs[0x148], 0x40, 0); 2550 Regs[0x1e0] |= ((duty_cycle >> 1) & 0x40); 2551 } 2552 2553 data_bitset (&dev->init_regs[0x148], 0x7f, Regs[0x148]); 2554 data_bitset (&dev->init_regs[0x1e0], 0x3f, Regs[0x1e0]); 2555 2556 Write_Byte (dev->usb_handle, 0xe948, Regs[0x0148]); 2557 2558 rst = Write_Byte (dev->usb_handle, 0xe9e0, Regs[0x01e0]); 2559 } 2560 2561 free (Regs); 2562 } 2563 2564 DBG (DBG_FNC, "- Lamp_PWM_DutyCycle_Set: %i\n", rst); 2565 2566 return rst; 2567} 2568 2569static SANE_Int 2570Head_ParkHome (struct st_device *dev, SANE_Int bWait, SANE_Int movement) 2571{ 2572 SANE_Int rst = ERROR; 2573 SANE_Byte *Regs; 2574 2575 DBG (DBG_FNC, "+ Head_ParkHome(bWait=%i, movement=%i):\n", bWait, movement); 2576 2577 Regs = (SANE_Byte *) malloc (RT_BUFFER_LEN * sizeof (SANE_Byte)); 2578 if (Regs != NULL) 2579 { 2580 rst = OK; 2581 2582 memcpy (Regs, dev->init_regs, RT_BUFFER_LEN * sizeof (SANE_Byte)); 2583 2584 /* Lets wait if it's required when is already executing */ 2585 if (bWait != FALSE) 2586 { 2587 if (RTS_WaitScanEnd (dev, 0x3a98) != OK) 2588 { 2589 DBG (DBG_FNC, " -> Head_ParkHome: RTS_WaitScanEnd Timeout\n"); 2590 rst = ERROR; /* timeout */ 2591 } 2592 } 2593 else 2594 { 2595 if (RTS_IsExecuting (dev, Regs) == FALSE) 2596 { 2597 DBG (DBG_FNC, 2598 " -> Head_ParkHome: RTS_IsExecuting = 0, exiting function\n"); 2599 rst = ERROR; /* if NOT executing */ 2600 } 2601 } 2602 2603 /* Check if lamp is at home */ 2604 if ((rst == OK) && (Head_IsAtHome (dev, Regs) == FALSE)) 2605 { 2606 struct st_motormove mymotor; 2607 struct st_motorpos mtrpos; 2608 2609 DBG (DBG_FNC, 2610 "-> Head_ParkHome: Lamp is not at home, lets move\n"); 2611 2612 /* it isn't */ 2613 dev->status->parkhome = TRUE; 2614 2615 if ((movement != -1) && (movement < dev->motormove_count)) 2616 { 2617 memcpy (&mymotor, dev->motormove[movement], 2618 sizeof (struct st_motormove)); 2619 } 2620 else 2621 { 2622 /* debug this code. Shouldn't have any relationship with offsets */ 2623 if (default_gain_offset->edcg2[CL_BLUE] < 4) 2624 mymotor.scanmotorsteptype = 2625 default_gain_offset->edcg2[CL_BLUE]; 2626 2627 mymotor.ctpc = default_gain_offset->odcg2[1]; 2628 mymotor.systemclock = default_gain_offset->edcg2[1]; /*? */ 2629 } 2630 2631 mtrpos.options = MTR_ENABLED | MTR_BACKWARD; 2632 mtrpos.v12e448 = 0x01; 2633 mtrpos.v12e44c = 0x00; 2634 mtrpos.coord_y = 0x4e20; 2635 2636 Motor_Move (dev, Regs, &mymotor, &mtrpos); 2637 2638 /* Should we wait? */ 2639 if (bWait != FALSE) 2640 rst = RTS_WaitScanEnd (dev, 15000); 2641 2642 dev->status->parkhome = FALSE; 2643 } 2644 2645 free (Regs); 2646 } 2647 2648 DBG (DBG_FNC, "- Head_ParkHome: %i:\n", rst); 2649 2650 return rst; 2651} 2652 2653static SANE_Int 2654Motor_Move (struct st_device *dev, SANE_Byte * Regs, 2655 struct st_motormove *mymotor, struct st_motorpos *mtrpos) 2656{ 2657 SANE_Byte *cpRegs; 2658 SANE_Int rst; 2659 2660 DBG (DBG_FNC, "+ Motor_Move:\n"); 2661 2662 rst = ERROR; 2663 2664 cpRegs = (SANE_Byte *) malloc (RT_BUFFER_LEN * sizeof (SANE_Byte)); 2665 if (cpRegs != NULL) 2666 { 2667 SANE_Int data, v12dcf8, coord_y, step_type; 2668 2669 memcpy (cpRegs, Regs, RT_BUFFER_LEN * sizeof (SANE_Byte)); 2670 v12dcf8 = 0; 2671 2672 /* resolution = 1 dpi */ 2673 data_bitset (&cpRegs[0xc0], 0x1f, 1); /*---xxxxx*/ 2674 2675 /* set motor step type */ 2676 data_bitset (&cpRegs[0xd9], 0x70, mymotor->scanmotorsteptype); /*-xxx----*/ 2677 2678 /* set motor direction (polarity) */ 2679 data_bitset (&cpRegs[0xd9], 0x80, mtrpos->options >> 3); /*e------- */ 2680 2681 /* next value doesn't seem to have any effect */ 2682 data_bitset (&cpRegs[0xd9], 0x0f, mtrpos->options); /*----efgh*/ 2683 2684 /* 0 enable/1 disable motor */ 2685 data_bitset (&cpRegs[0xdd], 0x80, mtrpos->options >> 4); /*d------- */ 2686 2687 /* next value doesn't seem to have any effect */ 2688 data_bitset (&cpRegs[0xdd], 0x40, mtrpos->options >> 4); /*-d------*/ 2689 2690 switch (mymotor->scanmotorsteptype) 2691 { 2692 case STT_OCT: 2693 step_type = 8; 2694 break; 2695 case STT_QUART: 2696 step_type = 4; 2697 break; 2698 case STT_HALF: 2699 step_type = 2; 2700 break; 2701 case STT_FULL: 2702 step_type = 1; 2703 break; 2704 default: 2705 step_type = 0; 2706 break; /* shouldn't be used */ 2707 } 2708 2709 coord_y = (mtrpos->coord_y * step_type) & 0xffff; 2710 if (coord_y < 2) 2711 coord_y = 2; 2712 2713 /* Sets dummyline to 1 */ 2714 data_bitset (&cpRegs[0xd6], 0xf0, 1); 2715 2716 /* set step_size - 1 */ 2717 cpRegs[0xe0] = 0; 2718 2719 cpRegs[0x01] &= 0xf9; 2720 cpRegs[0x01] |= (mtrpos->v12e448 & 1) << 2; 2721 2722 /* set dummy scan */ 2723 data_bitset (&cpRegs[0x01], 0x10, 1); /*---x----*/ 2724 2725 /* set samplerate */ 2726 data_bitset (&cpRegs[0x1cf], 0x40, PIXEL_RATE); /*-x------*/ 2727 2728 /* unknown data */ 2729 data_bitset (&cpRegs[0x1cf], 0x80, 1); /*x------- */ 2730 2731 /* sets one channel per color */ 2732 data_bitset (&cpRegs[0x12], 0x3f, 0); /* channel */ 2733 data_bitset (&cpRegs[0x12], 0xc0, 1); /* 1 channel */ 2734 2735 /* timing cnpp */ 2736 data_bitset (&cpRegs[0x96], 0x3f, 0x0b); /*--001011*/ 2737 2738 /* set systemclock */ 2739 data_bitset (&cpRegs[0x00], 0x0f, mymotor->systemclock); /*----xxxx*/ 2740 2741 /* set last step of accurve.smearing table to 2 */ 2742 data_lsb_set (&cpRegs[0xe4], 2, 3); 2743 2744 /* set last step of deccurve.scanbufferfull table to 16 */ 2745 data_lsb_set (&Regs[0xea], 0x10, 3); 2746 2747 /* set last step of deccurve.normalscan table to 16 */ 2748 data_lsb_set (&Regs[0xed], 0x10, 3); 2749 2750 /* set last step of deccurve.smearing table to 16 */ 2751 data_lsb_set (&Regs[0xf0], 0x10, 3); 2752 2753 /* set last step of deccurve.parkhome table to 16 */ 2754 data_lsb_set (&Regs[0xf3], 0x10, 3); 2755 2756 /* set msi */ 2757 cpRegs[0xda] = 2; 2758 cpRegs[0xdd] &= 0xfc; 2759 2760 /* set if motor has motorcurves */ 2761 data_bitset (&cpRegs[0xdf], 0x10, 2762 ((mymotor->motorcurve != -1) ? 1 : 0)); 2763 2764 if (mymotor->motorcurve != -1) 2765 { 2766 struct st_curve *crv; 2767 2768 /* set last step of accurve.normalscan table */ 2769 crv = 2770 Motor_Curve_Get (dev, mymotor->motorcurve, ACC_CURVE, 2771 CRV_NORMALSCAN); 2772 if (crv != NULL) 2773 data_lsb_set (&cpRegs[0xe1], crv->step[crv->step_count - 1], 3); 2774 2775 DBG (DBG_FNC, " -> Setting up stepper motor using motorcurve %i\n", 2776 mymotor->motorcurve); 2777 v12dcf8 = Motor_Setup_Steps (dev, cpRegs, mymotor->motorcurve); 2778 2779 /* set step_size - 1 */ 2780 cpRegs[0xe0] = 0; 2781 2782 crv = 2783 Motor_Curve_Get (dev, mymotor->motorcurve, DEC_CURVE, 2784 CRV_NORMALSCAN); 2785 if (crv != NULL) 2786 coord_y -= (v12dcf8 + crv->step_count); 2787 2788 /* set line exposure time */ 2789 data_lsb_set (&cpRegs[0x30], mymotor->ctpc, 3); 2790 2791 /* set last step of accurve.smearing table */ 2792 data_lsb_set (&cpRegs[0xe4], 0, 3); 2793 } 2794 else 2795 { 2796 /* Setting some motor step */ 2797 SANE_Int some_step; 2798 2799 switch (Regs[0x00] & 0x0f) 2800 { 2801 case 0x00: 2802 some_step = 0x00895440; 2803 break; /* 3 x 0x2DC6C0 */ 2804 case 0x08: 2805 case 0x01: 2806 some_step = 0x00b71b00; 2807 break; /* 4 x 0x2DC6C0 */ 2808 case 0x02: 2809 some_step = 0x0112a880; 2810 break; /* 6 x 0x2DC6C0 */ 2811 case 0x0a: 2812 case 0x03: 2813 some_step = 0x016e3600; 2814 break; /* 8 x 0x2DC6C0 */ 2815 case 0x04: 2816 some_step = 0x02255100; 2817 break; /* 12 x 0x2DC6C0 */ 2818 case 0x0c: 2819 some_step = 0x02dc6c00; 2820 break; /* 16 x 0x2DC6C0 */ 2821 case 0x05: 2822 some_step = 0x044aa200; 2823 break; /* 24 x 0x2DC6C0 */ 2824 case 0x0d: 2825 some_step = 0x05b8d800; 2826 break; /* 32 x 0x2DC6C0 */ 2827 2828 case 0x09: 2829 some_step = 0x00f42400; 2830 break; 2831 case 0x0b: 2832 some_step = 0x01e84800; 2833 break; /* = case 9 * 2 */ 2834 default: 2835 some_step = 0x0478f7f8; 2836 break; 2837 } 2838 2839 /* divide by timing.cnpp */ 2840 some_step /= ((cpRegs[0x96] & 0x3f) + 1); 2841 if (mymotor->ctpc > 0) 2842 some_step /= mymotor->ctpc; 2843 2844 /* set line exposure time */ 2845 data_lsb_set (&cpRegs[0x30], some_step, 3); 2846 2847 /* set last step of accurve.normalscan table */ 2848 data_lsb_set (&cpRegs[0xe1], some_step, 3); 2849 } 2850 2851 /* Setting coords */ 2852 RTS_Setup_Coords (cpRegs, 100, coord_y - 1, 800, 1); 2853 2854 /* enable head movement */ 2855 data_bitset (&cpRegs[0xd8], 0x80, 1); 2856 2857 /* release motor before executing */ 2858 Motor_Release (dev); 2859 2860 RTS_Warm_Reset (dev); 2861 2862 /* action! */ 2863 data = RTS_WriteRegs (dev->usb_handle, cpRegs); 2864 if (data == OK) 2865 RTS_Execute (dev); 2866 2867 /* wait 10 seconds */ 2868 RTS_WaitScanEnd (dev, 10000); 2869 2870 rst = (data != OK) ? v12dcf8 : RTS_WaitScanEnd (dev, 20000); 2871 2872 free (cpRegs); 2873 } 2874 2875 DBG (DBG_FNC, "- Motor_Move: %i\n", rst); 2876 2877 return rst; 2878} 2879 2880static void 2881Free_Motormoves (struct st_device *dev) 2882{ 2883 DBG (DBG_FNC, "> Free_Motormoves\n"); 2884 2885 if (dev->motormove != NULL) 2886 { 2887 SANE_Int a; 2888 struct st_motormove *ms; 2889 2890 for (a = 0; a < dev->motormove_count; a++) 2891 { 2892 ms = dev->motormove[a]; 2893 if (ms != NULL) 2894 free (ms); 2895 } 2896 2897 free (dev->motormove); 2898 dev->motormove = NULL; 2899 } 2900 2901 dev->motormove_count = 0; 2902} 2903 2904static void 2905Free_MotorCurves (struct st_device *dev) 2906{ 2907 DBG (DBG_FNC, "> Free_MotorCurves\n"); 2908 if (dev->mtrsetting != NULL) 2909 Motor_Curve_Free (dev->mtrsetting, &dev->mtrsetting_count); 2910 2911 dev->mtrsetting = NULL; 2912 dev->mtrsetting_count = 0; 2913} 2914 2915static SANE_Int 2916Load_MotorCurves (struct st_device *dev) 2917{ 2918 SANE_Int rst = ERROR; 2919 SANE_Int *mtc = NULL; 2920 2921 if (dev->mtrsetting != NULL) 2922 Free_MotorCurves (dev); 2923 2924 DBG (DBG_FNC, "> Load_MotorCurves\n"); 2925 2926 /* get motor settings buffer for this device */ 2927 mtc = cfg_motorcurve_get (); 2928 if (mtc != NULL) 2929 { 2930 /* parse buffer to get all motorcurves */ 2931 dev->mtrsetting = Motor_Curve_Parse (&dev->mtrsetting_count, mtc); 2932 if (dev->mtrsetting != NULL) 2933 rst = OK; 2934 } 2935 2936 if (rst != ERROR) 2937 { 2938 DBG (DBG_FNC, " -> Found %i motor settings\n", dev->mtrsetting_count); 2939 dbg_motorcurves (dev); 2940 } 2941 else 2942 DBG (DBG_ERR, "- Load_MotorCurves error!!\n"); 2943 2944 return rst; 2945} 2946 2947static SANE_Int 2948Load_Motormoves (struct st_device *dev) 2949{ 2950 SANE_Int rst = OK; 2951 SANE_Int a; 2952 struct st_motormove reg, *mm; 2953 2954 DBG (DBG_FNC, "> Load_Motormoves\n"); 2955 2956 /* if there is already any movement loaded let's free it */ 2957 if (dev->motormove != NULL) 2958 Free_Motormoves (dev); 2959 2960 a = 0; 2961 while ((cfg_motormove_get (dev->sensorcfg->type, a, ®) != ERROR) 2962 && (rst == OK)) 2963 { 2964 dev->motormove_count++; 2965 dev->motormove = 2966 (struct st_motormove **) realloc (dev->motormove, 2967 sizeof (struct st_motormove **) * 2968 dev->motormove_count); 2969 if (dev->motormove != NULL) 2970 { 2971 mm = (struct st_motormove *) malloc (sizeof (struct st_motormove)); 2972 if (mm != NULL) 2973 { 2974 memcpy (mm, ®, sizeof (struct st_motormove)); 2975 dev->motormove[dev->motormove_count - 1] = mm; 2976 } 2977 else 2978 rst = ERROR; 2979 } 2980 else 2981 rst = ERROR; 2982 2983 a++; 2984 } 2985 2986 if (rst == ERROR) 2987 Free_Motormoves (dev); 2988 2989 DBG (DBG_FNC, " -> Found %i motormoves\n", dev->motormove_count); 2990 dbg_motormoves (dev); 2991 2992 return rst; 2993} 2994 2995static SANE_Byte * 2996Motor_AddStep (SANE_Byte * steps, SANE_Int * bwriten, SANE_Int step) 2997{ 2998 steps = (SANE_Byte *) realloc (steps, sizeof (SANE_Byte) * (*bwriten + 3)); 2999 if (steps != NULL) 3000 { 3001 data_msb_set (&steps[*bwriten], step, 3); 3002 *bwriten += 3; 3003 } 3004 else 3005 *bwriten = 0; 3006 3007 return steps; 3008} 3009 3010static SANE_Int 3011Motor_Setup_Steps (struct st_device *dev, SANE_Byte * Regs, 3012 SANE_Int mysetting) 3013{ 3014 SANE_Int varx10, cont, last_acc_step, varx20, stepbuffer_size, 3015 mystep, bwriten; 3016 SANE_Int myvar, var1, myvalor, mybwriten; 3017 struct st_curve *mycurve; 3018 SANE_Byte *steps; 3019 3020 DBG (DBG_FNC, "+ Motor_Setup_Steps(*Regs, motorsetting=%i):\n", mysetting); 3021 3022 varx10 = 0; 3023 cont = 0; 3024 varx20 = 0; 3025 stepbuffer_size = (v15f8 << 4) & 0xffff; 3026 steps = NULL; 3027 bwriten = 0; 3028 deccurvecount = 0; 3029 acccurvecount = 0; 3030 last_acc_step = 0; 3031 3032 /* mycurve points to acc normalscan steps table */ 3033 mycurve = Motor_Curve_Get (dev, mysetting, ACC_CURVE, CRV_NORMALSCAN); 3034 3035 if (mycurve != NULL) 3036 { 3037 /* acccurvecount has the number of steps in acc normalscan table */ 3038 acccurvecount = mycurve->step_count; 3039 3040 /* get last acccurve step from acc.normalscan step table */ 3041 last_acc_step = data_lsb_get (&Regs[0xe1], 3); 3042 3043 /* sets pointer to acc.normalscan step table */ 3044 data_wide_bitset (&Regs[0xf6], 0x3fff, stepbuffer_size); 3045 3046 /* Separate each step in three bytes */ 3047 if (mycurve->step_count > 0) 3048 for (cont = 0; cont < mycurve->step_count; cont++) 3049 { 3050 mystep = mycurve->step[cont]; 3051 if (mystep <= last_acc_step) 3052 { 3053 acccurvecount = cont; 3054 break; 3055 } 3056 varx20 += mystep + 1; 3057 steps = Motor_AddStep (steps, &bwriten, mystep); 3058 } 3059 } 3060 3061 if (acccurvecount == 0) 3062 { 3063 /* Write one step (last_acc_step + 0x01) to buffer */ 3064 acccurvecount++; 3065 varx20 += (last_acc_step + 1) + 1; 3066 steps = Motor_AddStep (steps, &bwriten, last_acc_step + 1); 3067 } 3068 3069 /* write another step (last_acc_step) */ 3070 acccurvecount++; 3071 varx20 += last_acc_step + 1; 3072 steps = Motor_AddStep (steps, &bwriten, last_acc_step); 3073 3074 /* get line exposure time */ 3075 myvar = data_lsb_get (&Regs[0x30], 3) + 1; 3076 3077 var1 = (varx20 + myvar - 1) / myvar; 3078 var1 = ((var1 * myvar) + mycurve->step[0] - varx20) - 0x0d; 3079 if (steps != NULL) 3080 data_msb_set (&steps[0], var1, 3); 3081 3082 /* dec.scanbufferfull step table */ 3083 /* set pointer to next table */ 3084 stepbuffer_size += (acccurvecount * 3); 3085 data_wide_bitset (&Regs[0xf8], 0x3fff, stepbuffer_size); 3086 3087 /* set last step of deccurve.scanbufferfull table */ 3088 mycurve = Motor_Curve_Get (dev, mysetting, DEC_CURVE, CRV_BUFFERFULL); 3089 deccurvecount = mycurve->step_count; 3090 data_lsb_set (&Regs[0xea], mycurve->step[mycurve->step_count - 1], 3); 3091 3092 /* write another step mycurve->step_count,cont,last_acc_step */ 3093 deccurvecount++; 3094 steps = Motor_AddStep (steps, &bwriten, last_acc_step); 3095 3096 /* Separate each step in three bytes */ 3097 if (mycurve->step_count > 1) 3098 for (cont = 0; cont < (mycurve->step_count - 1); cont++) 3099 { 3100 mystep = mycurve->step[cont]; 3101 if (mystep > last_acc_step) 3102 steps = Motor_AddStep (steps, &bwriten, mystep); 3103 else 3104 deccurvecount--; 3105 } 3106 3107 myvalor = dev->mtrsetting[mysetting]->motorbackstep; 3108 if (myvalor > 0) 3109 { 3110 SANE_Int step_size = _B0 (Regs[0xe0]) + 1; 3111 3112 myvalor = ((myvalor - deccurvecount) - acccurvecount) + 2; 3113 varx10 = myvalor; 3114 myvalor /= step_size; 3115 myvalor *= step_size; 3116 var1 = mycurve->step[mycurve->step_count - 1]; /* last deccurve step */ 3117 if (last_acc_step >= var1) 3118 var1 = last_acc_step + 1; 3119 deccurvecount += (varx10 - myvalor); 3120 myvalor = varx10 - myvalor; 3121 } 3122 else 3123 myvalor = varx10; 3124 3125 if (myvalor > 0) 3126 for (cont = myvalor; cont > 0; cont--) 3127 steps = Motor_AddStep (steps, &bwriten, var1 - 1); 3128 3129 /* write another step , bwriten tiene 4b */ 3130 steps = Motor_AddStep (steps, &bwriten, var1); 3131 3132 /* acc.smearing step table */ 3133 if (Motor_Curve_Get (dev, mysetting, ACC_CURVE, CRV_SMEARING) != NULL) 3134 { 3135 /* acc.smearing curve enabled */ 3136 if (Motor_Curve_Equal 3137 (dev, mysetting, ACC_CURVE, CRV_SMEARING, CRV_NORMALSCAN) == TRUE) 3138 { 3139 /* acc.smearing pointer points to acc.normalscan table */ 3140 data_wide_bitset (&Regs[0xfa], 0x3fff, 3141 data_lsb_get (&Regs[0xf6], 2)); 3142 /* last step of acc.smearing table is the same as acc.normalscan */ 3143 data_lsb_set (&Regs[0xe4], data_lsb_get (&Regs[0xe1], 3), 3); 3144 } 3145 else 3146 { 3147 /* set pointer to next step table */ 3148 stepbuffer_size += (deccurvecount * 3); 3149 data_wide_bitset (&Regs[0xfa], 0x3fff, stepbuffer_size); 3150 3151 /* set last step of acc.smearing table */ 3152 mycurve = Motor_Curve_Get (dev, mysetting, ACC_CURVE, CRV_SMEARING); 3153 if (mycurve != NULL) 3154 { 3155 smearacccurvecount = mycurve->step_count; 3156 data_lsb_set (&Regs[0xe4], 3157 mycurve->step[mycurve->step_count - 1], 3); 3158 3159 /* generate acc.smearing table */ 3160 if (mycurve->step_count > 0) 3161 for (cont = 0; cont < mycurve->step_count; cont++) 3162 steps = 3163 Motor_AddStep (steps, &bwriten, mycurve->step[cont]); 3164 } 3165 } 3166 } 3167 else 3168 { 3169 /* acc.smearing curve disabled */ 3170 data_wide_bitset (&Regs[0xfa], 0x3fff, 0); 3171 } 3172 3173 /* dec.smearing */ 3174 if (Motor_Curve_Get (dev, mysetting, DEC_CURVE, CRV_SMEARING) != NULL) 3175 { 3176 /* dec.smearing curve enabled */ 3177 if (Motor_Curve_Equal 3178 (dev, mysetting, DEC_CURVE, CRV_SMEARING, CRV_BUFFERFULL) == TRUE) 3179 { 3180 /* dec.smearing pointer points to dec.scanbufferfull table */ 3181 data_wide_bitset (&Regs[0x00fc], 0x3fff, 3182 data_lsb_get (&Regs[0x00f8], 2)); 3183 /* last step of dec.smearing table is the same as dec.scanbufferfull */ 3184 data_lsb_set (&Regs[0x00f0], data_lsb_get (&Regs[0x00ea], 3), 3); 3185 } 3186 else 3187 { 3188 /* set pointer to next step table */ 3189 if (mycurve != NULL) 3190 stepbuffer_size += (mycurve->step_count * 3); 3191 data_wide_bitset (&Regs[0xfc], 0x3fff, stepbuffer_size); 3192 3193 /* set last step of dec.smearing table */ 3194 mycurve = Motor_Curve_Get (dev, mysetting, DEC_CURVE, CRV_SMEARING); 3195 if (mycurve != NULL) 3196 { 3197 smeardeccurvecount = mycurve->step_count; 3198 data_lsb_set (&Regs[0xf0], 3199 mycurve->step[mycurve->step_count - 1], 3); 3200 3201 /* generate dec.smearing table */ 3202 if (mycurve->step_count > 0) 3203 for (cont = 0; cont < mycurve->step_count; cont++) 3204 steps = 3205 Motor_AddStep (steps, &bwriten, mycurve->step[cont]); 3206 } 3207 } 3208 } 3209 else 3210 { 3211 /* dec.smearing curve disabled */ 3212 data_wide_bitset (&Regs[0x00fc], 0x3fff, 0); 3213 } 3214 3215 /* dec.normalscan */ 3216 if (Motor_Curve_Get (dev, mysetting, DEC_CURVE, CRV_NORMALSCAN) != NULL) 3217 { 3218 /* dec.normalscan enabled */ 3219 if (Motor_Curve_Equal 3220 (dev, mysetting, DEC_CURVE, CRV_NORMALSCAN, CRV_BUFFERFULL) == TRUE) 3221 { 3222 /* dec.normalscan pointer points to dec.scanbufferfull table */ 3223 data_wide_bitset (&Regs[0xfe], 0x3fff, 3224 data_lsb_get (&Regs[0xf8], 2)); 3225 /* last step of dec.normalscan table is the same as dec.scanbufferfull */ 3226 data_lsb_set (&Regs[0xed], data_lsb_get (&Regs[0xea], 3), 3); 3227 } 3228 else 3229 if (Motor_Curve_Equal 3230 (dev, mysetting, DEC_CURVE, CRV_NORMALSCAN, CRV_SMEARING) == TRUE) 3231 { 3232 /* dec.normalscan pointer points to dec.smearing table */ 3233 data_wide_bitset (&Regs[0xfe], 0x3fff, 3234 data_lsb_get (&Regs[0xfc], 2)); 3235 /* last step of dec.normalscan table is the same as dec.smearing */ 3236 data_lsb_set (&Regs[0xed], data_lsb_get (&Regs[0xf0], 3), 3); 3237 } 3238 else 3239 { 3240 /* set pointer to next step table */ 3241 if (mycurve != NULL) 3242 stepbuffer_size += (mycurve->step_count * 3); 3243 data_wide_bitset (&Regs[0xfe], 0x3fff, stepbuffer_size); 3244 3245 /* set last step of dec.normalscan table */ 3246 mycurve = 3247 Motor_Curve_Get (dev, mysetting, DEC_CURVE, CRV_NORMALSCAN); 3248 if (mycurve != NULL) 3249 { 3250 data_lsb_set (&Regs[0xed], 3251 mycurve->step[mycurve->step_count - 1], 3); 3252 3253 /* generate dec.normalscan table */ 3254 if (mycurve->step_count > 0) 3255 for (cont = 0; cont < mycurve->step_count; cont++) 3256 steps = 3257 Motor_AddStep (steps, &bwriten, mycurve->step[cont]); 3258 } 3259 } 3260 } 3261 else 3262 { 3263 /* dec.normalscan disabled */ 3264 data_wide_bitset (&Regs[0xfe], 0x3fff, 0); 3265 } 3266 3267 /* acc.parkhome */ 3268 if (Motor_Curve_Get (dev, mysetting, ACC_CURVE, CRV_PARKHOME) != NULL) 3269 { 3270 /* parkhome curve enabled */ 3271 3272 if (Motor_Curve_Equal 3273 (dev, mysetting, ACC_CURVE, CRV_PARKHOME, CRV_NORMALSCAN) == TRUE) 3274 { 3275 /* acc.parkhome pointer points to acc.normalscan table */ 3276 data_wide_bitset (&Regs[0x100], 0x3fff, 3277 data_lsb_get (&Regs[0xf6], 2)); 3278 3279 /* last step of acc.parkhome table is the same as acc.normalscan */ 3280 data_lsb_set (&Regs[0xe7], data_lsb_get (&Regs[0xe1], 3), 3); 3281 } 3282 else 3283 if (Motor_Curve_Equal 3284 (dev, mysetting, ACC_CURVE, CRV_PARKHOME, CRV_SMEARING) == TRUE) 3285 { 3286 /* acc.parkhome pointer points to acc.smearing table */ 3287 data_wide_bitset (&Regs[0x100], 0x3fff, 3288 data_lsb_get (&Regs[0xfa], 2)); 3289 /* last step of acc.parkhome table is the same as acc.smearing */ 3290 data_lsb_set (&Regs[0xe7], data_lsb_get (&Regs[0xe4], 3), 3); 3291 } 3292 else 3293 { 3294 /* set pointer to next step table */ 3295 if (mycurve != NULL) 3296 stepbuffer_size += (mycurve->step_count * 3); 3297 data_wide_bitset (&Regs[0x100], 0x3fff, stepbuffer_size); 3298 3299 /* set last step of acc.parkhome table */ 3300 mycurve = Motor_Curve_Get (dev, mysetting, ACC_CURVE, CRV_PARKHOME); 3301 if (mycurve != NULL) 3302 { 3303 data_lsb_set (&Regs[0xe7], 3304 mycurve->step[mycurve->step_count - 1], 3); 3305 3306 /* generate acc.parkhome table */ 3307 if (mycurve->step_count > 0) 3308 for (cont = 0; cont < mycurve->step_count; cont++) 3309 steps = 3310 Motor_AddStep (steps, &bwriten, mycurve->step[cont]); 3311 } 3312 } 3313 } 3314 else 3315 { 3316 /* parkhome curve is disabled */ 3317 /* acc.parkhome pointer points to 0 */ 3318 data_wide_bitset (&Regs[0x100], 0x3fff, 0); 3319 data_lsb_set (&Regs[0xe7], 16, 3); 3320 } 3321 3322 /* dec.parkhome */ 3323 if (Motor_Curve_Get (dev, mysetting, DEC_CURVE, CRV_PARKHOME) != NULL) 3324 { 3325 /* parkhome curve enabled */ 3326 if (Motor_Curve_Equal 3327 (dev, mysetting, DEC_CURVE, CRV_PARKHOME, CRV_BUFFERFULL) == TRUE) 3328 { 3329 /* dec.parkhome pointer points to dec.scanbufferfull table */ 3330 data_wide_bitset (&Regs[0x102], 0x3fff, 3331 data_lsb_get (&Regs[0xf8], 2)); 3332 /* last step of dec.parkhome table is the same as dec.scanbufferfull */ 3333 data_lsb_set (&Regs[0xf3], data_lsb_get (&Regs[0xe4], 3), 3); 3334 } 3335 else 3336 if (Motor_Curve_Equal 3337 (dev, mysetting, DEC_CURVE, CRV_PARKHOME, CRV_SMEARING) == TRUE) 3338 { 3339 /* dec.parkhome pointer points to dec.smearing table */ 3340 data_wide_bitset (&Regs[0x102], 0x3fff, 3341 data_lsb_get (&Regs[0xfe], 2)); 3342 /* last step of dec.parkhome table is the same as dec.smearing */ 3343 data_lsb_set (&Regs[0xf3], data_lsb_get (&Regs[0xf0], 3), 3); 3344 } 3345 else 3346 if (Motor_Curve_Equal 3347 (dev, mysetting, DEC_CURVE, CRV_PARKHOME, CRV_NORMALSCAN) == TRUE) 3348 { 3349 /* dec.parkhome pointer points to dec.normalscan table */ 3350 data_wide_bitset (&Regs[0x102], 0x3fff, 3351 data_lsb_get (&Regs[0xfe], 2)); 3352 /* last step of dec.parkhome table is the same as dec.normalscan */ 3353 data_lsb_set (&Regs[0xf3], data_lsb_get (&Regs[0xed], 3), 3); 3354 } 3355 else 3356 { 3357 /* set pointer to next step table */ 3358 if (mycurve != NULL) 3359 stepbuffer_size += (mycurve->step_count * 3); 3360 data_wide_bitset (&Regs[0x102], 0x3fff, stepbuffer_size); 3361 3362 /* set last step of dec.parkhome table */ 3363 mycurve = Motor_Curve_Get (dev, mysetting, DEC_CURVE, CRV_PARKHOME); 3364 if (mycurve != NULL) 3365 { 3366 data_lsb_set (&Regs[0xf3], 3367 mycurve->step[mycurve->step_count - 1], 3); 3368 3369 /* generate dec.parkhome table */ 3370 if (mycurve->step_count > 0) 3371 for (cont = 0; cont < mycurve->step_count; cont++) 3372 steps = 3373 Motor_AddStep (steps, &bwriten, mycurve->step[cont]); 3374 } 3375 } 3376 } 3377 else 3378 { 3379 /* parkhome curve is disabled */ 3380 3381 /* dec.parkhome pointer points to 0 */ 3382 data_wide_bitset (&Regs[0x102], 0x3fff, 0); 3383 data_lsb_set (&Regs[0xf3], 16, 3); 3384 } 3385 3386 mybwriten = bwriten & 0x8000000f; 3387 if (mybwriten < 0) 3388 mybwriten = ((mybwriten - 1) | 0xfffffff0) + 1; 3389 3390 if (mybwriten != 0) 3391 bwriten = (((bwriten & 0xffff) >> 0x04) + 1) << 0x04; 3392 bwriten = bwriten & 0xffff; 3393 3394 /* display table */ 3395 DBG (DBG_FNC, " -> Direction Type Offset Last step\n"); 3396 DBG (DBG_FNC, " -> --------- -------------- ------ ---------\n"); 3397 DBG (DBG_FNC, " -> ACC_CURVE CRV_NORMALSCAN %6i %6i\n", 3398 data_lsb_get (&Regs[0x0f6], 2) & 0x3fff, data_lsb_get (&Regs[0x0e1], 3399 3)); 3400 DBG (DBG_FNC, " -> ACC_CURVE CRV_SMEARING %6i %6i\n", 3401 data_lsb_get (&Regs[0x0fa], 2) & 0x3fff, data_lsb_get (&Regs[0x0e4], 3402 3)); 3403 DBG (DBG_FNC, " -> ACC_CURVE CRV_PARKHOME %6i %6i\n", 3404 data_lsb_get (&Regs[0x100], 2) & 0x3fff, data_lsb_get (&Regs[0x0e7], 3405 3)); 3406 DBG (DBG_FNC, " -> DEC_CURVE CRV_NORMALSCAN %6i %6i\n", 3407 data_lsb_get (&Regs[0x0fe], 2) & 0x3fff, data_lsb_get (&Regs[0x0ed], 3408 3)); 3409 DBG (DBG_FNC, " -> DEC_CURVE CRV_SMEARING %6i %6i\n", 3410 data_lsb_get (&Regs[0x0fc], 2) & 0x3fff, data_lsb_get (&Regs[0x0f0], 3411 3)); 3412 DBG (DBG_FNC, " -> DEC_CURVE CRV_PARKHOME %6i %6i\n", 3413 data_lsb_get (&Regs[0x102], 2) & 0x3fff, data_lsb_get (&Regs[0x0f3], 3414 3)); 3415 DBG (DBG_FNC, " -> DEC_CURVE CRV_BUFFERFULL %6i %6i\n", 3416 data_lsb_get (&Regs[0x0f8], 2) & 0x3fff, data_lsb_get (&Regs[0x0ea], 3417 3)); 3418 3419 RTS_Warm_Reset (dev); 3420 3421 /* send motor steps */ 3422 if (steps != NULL) 3423 { 3424 if (bwriten > 0) 3425 { 3426 /* lock */ 3427 SetLock (dev->usb_handle, Regs, TRUE); 3428 3429 /* send steps */ 3430 RTS_DMA_Write (dev, 0x0000, v15f8, bwriten, steps); 3431 3432 /* unlock */ 3433 SetLock (dev->usb_handle, Regs, FALSE); 3434 } 3435 3436 free (steps); 3437 } 3438 3439 DBG (DBG_FNC, "- Motor_Setup_Steps: %i\n", acccurvecount); 3440 3441 return acccurvecount; 3442} 3443 3444static SANE_Int 3445Lamp_PWM_use (struct st_device *dev, SANE_Int enable) 3446{ 3447 SANE_Byte a, b; 3448 SANE_Int rst = ERROR; 3449 3450 DBG (DBG_FNC, "+ Lamp_PWM_use(enable=%i):\n", enable); 3451 3452 if (Read_Byte (dev->usb_handle, 0xe948, &a) == OK) 3453 { 3454 if (Read_Byte (dev->usb_handle, 0xe9e0, &b) == OK) 3455 { 3456 if (enable != 0) 3457 { 3458 if (pwmlamplevel != 0x00) 3459 { 3460 b |= 0x80; 3461 dev->init_regs[0x01e0] &= 0x3f; 3462 dev->init_regs[0x01e0] |= 0x80; 3463 } 3464 else 3465 { 3466 a |= 0x40; 3467 b &= 0x3f; 3468 dev->init_regs[0x0148] |= 0x40; 3469 dev->init_regs[0x01e0] &= 0x3f; 3470 } 3471 } 3472 else 3473 { 3474 b &= 0x7f; 3475 a &= 0xbf; 3476 } 3477 3478 if (Write_Byte (dev->usb_handle, 0xe948, a) == OK) 3479 rst = Write_Byte (dev->usb_handle, 0xe9e0, b); 3480 } 3481 } 3482 3483 DBG (DBG_FNC, "- Lamp_PWM_use: %i\n", rst); 3484 3485 return rst; 3486} 3487 3488static SANE_Int 3489SSCG_Enable (struct st_device *dev) 3490{ 3491 SANE_Int rst; 3492 SANE_Int sscg; 3493 SANE_Byte data1, data2; 3494 SANE_Int enable, mode, clock; 3495 3496 DBG (DBG_FNC, "+ SSCG_Enable:\n"); 3497 3498 rst = cfg_sscg_get (&enable, &mode, &clock); 3499 3500 if (rst == OK) 3501 { 3502 if ((Read_Byte (dev->usb_handle, 0xfe3a, &data1) == OK) 3503 && (Read_Byte (dev->usb_handle, 0xfe39, &data2) == OK)) 3504 { 3505 if (enable != FALSE) 3506 { 3507 /* clock values: 0=0.25%; 1=0.50%; 2=0.75%; 3=1.00% */ 3508 data2 = (mode == 0) ? data2 & 0x7f : data2 | 0x80; 3509 3510 sscg = (data1 & 0xf3) | (((clock & 0x03) | 0x04) << 0x02); 3511 sscg = (sscg << 8) | data2; 3512 } 3513 else 3514 sscg = ((data1 & 0xef) << 8) | _B0 (data2); 3515 3516 rst = Write_Word (dev->usb_handle, 0xfe39, sscg); 3517 } 3518 else 3519 rst = ERROR; 3520 } 3521 3522 DBG (DBG_FNC, "- SSCG_Enable: %i\n", rst); 3523 3524 return rst; 3525} 3526 3527static void 3528RTS_Setup_RefVoltages (struct st_device *dev, SANE_Byte * Regs) 3529{ 3530 /* this function sets top, midle and bottom reference voltages */ 3531 3532 DBG (DBG_FNC, "> RTS_Setup_RefVoltages\n"); 3533 3534 if (Regs != NULL) 3535 { 3536 SANE_Byte vrts, vrms, vrbs; 3537 3538 cfg_refvoltages_get (dev->sensorcfg->type, &vrts, &vrms, &vrbs); 3539 3540 /* Top Reference Voltage */ 3541 data_bitset (&Regs[0x14], 0xe0, vrts); /*xxx----- */ 3542 3543 /* Middle Reference Voltage */ 3544 data_bitset (&Regs[0x15], 0xe0, vrms); /*xxx----- */ 3545 3546 /* Bottom Reference Voltage */ 3547 data_bitset (&Regs[0x16], 0xe0, vrbs); /*xxx----- */ 3548 } 3549} 3550 3551static SANE_Int 3552Init_USBData (struct st_device *dev) 3553{ 3554 SANE_Byte data; 3555 SANE_Byte *resource; 3556 3557 DBG (DBG_FNC, "+ Init_USBData:\n"); 3558 3559 if (Read_Byte (dev->usb_handle, 0xf8ff, &data) != OK) 3560 return ERROR; 3561 3562 data = (data | 1); 3563 if (Write_Byte (dev->usb_handle, 0xf8ff, data) != OK) 3564 return ERROR; 3565 3566 if (SSCG_Enable (dev) != OK) 3567 return ERROR; 3568 3569 Init_Registers (dev); 3570 3571 /* Gamma table size = 0x100 */ 3572 data_bitset (&dev->init_regs[0x1d0], 0x30, 0x00); /*--00----*/ 3573 3574 /* Set 3 channels_per_dot */ 3575 data_bitset (&dev->init_regs[0x12], 0xc0, 0x03); /*xx------ */ 3576 3577 /* systemclock */ 3578 data_bitset (&dev->init_regs[0x00], 0x0f, 0x05); /*----xxxx*/ 3579 3580 /* timing cnpp */ 3581 data_bitset (&dev->init_regs[0x96], 0x3f, 0x17); /*--xxxxxx*/ 3582 3583 /* set sensor_channel_color_order */ 3584 data_bitset (&dev->init_regs[0x60a], 0x7f, 0x24); /*-xxxxxxx*/ 3585 3586 /* set crvs */ 3587 data_bitset (&dev->init_regs[0x10], 0x1f, get_value (SCAN_PARAM, CRVS, 7, usbfile)); /*---xxxxx*/ 3588 3589 /* set reference voltages */ 3590 RTS_Setup_RefVoltages (dev, dev->init_regs); 3591 3592 dev->init_regs[0x11] |= 0x10; 3593 3594 data_bitset (&dev->init_regs[0x26], 0x70, 5); /*-101----*/ 3595 3596 dev->init_regs[0x185] = 0x88; 3597 dev->init_regs[0x186] = 0x88; 3598 3599 /* SDRAM clock */ 3600 data = get_value (SCAN_PARAM, MCLKIOC, 8, usbfile); 3601 data_bitset (&dev->init_regs[0x187], 0x0f, 0x08); /*----xxxx*/ 3602 data_bitset (&dev->init_regs[0x187], 0xf0, data); /*xxxx---- */ 3603 3604 data--; 3605 3606 if (data < 7) 3607 { 3608 switch (data) 3609 { 3610 case 0: 3611 data |= 0xc0; 3612 break; 3613 case 1: 3614 data |= 0xa0; 3615 break; 3616 case 2: 3617 data |= 0xe0; 3618 break; 3619 case 3: 3620 data |= 0x90; 3621 break; 3622 case 4: 3623 data |= 0xd0; 3624 break; 3625 case 5: 3626 data |= 0xb0; 3627 break; 3628 case 6: 3629 data = (data & 0x0f); 3630 break; 3631 } 3632 dev->init_regs[0x187] = _B0 (data); 3633 } 3634 3635 data_bitset (&dev->init_regs[0x26], 0x0f, 0); /*----0000*/ 3636 3637 dev->init_regs[0x27] &= 0x3f; 3638 dev->init_regs[0x29] = 0x24; 3639 dev->init_regs[0x2a] = 0x10; 3640 dev->init_regs[0x150] = 0xff; 3641 dev->init_regs[0x151] = 0x13; 3642 dev->init_regs[0x156] = 0xf0; 3643 dev->init_regs[0x157] = 0xfd; 3644 3645 if (dev->motorcfg->changemotorcurrent != FALSE) 3646 Motor_Change (dev, dev->init_regs, 3); 3647 3648 dev->init_regs[0xde] = 0; 3649 data_bitset (&dev->init_regs[0xdf], 0x0f, 0); 3650 3651 /* loads motor resource for this dev */ 3652 resource = cfg_motor_resource_get (&data); 3653 if ((resource != NULL) && (data > 1)) 3654 memcpy (&dev->init_regs[0x104], resource, data); 3655 3656 /* this bit is set but I don't know its purpose */ 3657 dev->init_regs[0x01] |= 0x40; /*-1------*/ 3658 3659 dev->init_regs[0x124] = 0x94; 3660 3661 /* release motor */ 3662 Motor_Release (dev); 3663 3664 DBG (DBG_FNC, "- Init_USBData:\n"); 3665 3666 return OK; 3667} 3668 3669static SANE_Int 3670Init_Registers (struct st_device *dev) 3671{ 3672 SANE_Int rst = OK; 3673 3674 DBG (DBG_FNC, "+ Init_Registers:\n"); 3675 3676 /* Lee dev->init_regs */ 3677 memset (dev->init_regs, 0, RT_BUFFER_LEN); 3678 RTS_ReadRegs (dev->usb_handle, dev->init_regs); 3679 Read_FE3E (dev, &v1619); 3680 3681 if (dev->sensorcfg->type == CCD_SENSOR) 3682 { 3683 /* CCD sensor */ 3684 data_bitset (&dev->init_regs[0x11], 0xc0, 0); /*xx------ */ 3685 data_bitset (&dev->init_regs[0x146], 0x80, 1); /*x------- */ 3686 data_bitset (&dev->init_regs[0x146], 0x40, 1); /*-x------*/ 3687 3688 } 3689 else 3690 { 3691 /* CIS sensor */ 3692 data_bitset (&dev->init_regs[0x146], 0x80, 0); /*0------- */ 3693 data_bitset (&dev->init_regs[0x146], 0x40, 0); /*-0------*/ 3694 data_bitset (&dev->init_regs[0x11], 0xc0, 2); /*xx------ */ 3695 data_bitset (&dev->init_regs[0xae], 0x3f, 0x14); /*--xxxxxx*/ 3696 data_bitset (&dev->init_regs[0xaf], 0x07, 1); /*-----xxx*/ 3697 3698 dev->init_regs[0x9c] = dev->init_regs[0xa2] = dev->init_regs[0xa8] = 3699 (RTS_Debug->dev_model != UA4900) ? 1 : 0; 3700 dev->init_regs[0x9d] = dev->init_regs[0xa3] = dev->init_regs[0xa9] = 0; 3701 dev->init_regs[0x9e] = dev->init_regs[0xa4] = dev->init_regs[0xaa] = 0; 3702 dev->init_regs[0x9f] = dev->init_regs[0xa5] = dev->init_regs[0xab] = 0; 3703 dev->init_regs[0xa0] = dev->init_regs[0xa6] = dev->init_regs[0xac] = 0; 3704 dev->init_regs[0xa1] = dev->init_regs[0xa7] = dev->init_regs[0xad] = 3705 (RTS_Debug->dev_model != UA4900) ? 0x80 : 0; 3706 } 3707 3708 /* disable CCD channels */ 3709 data_bitset (&dev->init_regs[0x10], 0xe0, 0); /*xxx----- */ 3710 data_bitset (&dev->init_regs[0x13], 0x80, 0); /*x------- */ 3711 3712 /* enable timer to switch off lamp */ 3713 data_bitset (&dev->init_regs[0x146], 0x10, 1); /*---x----*/ 3714 3715 /* set time to switch off lamp */ 3716 dev->init_regs[0x147] = 0xff; 3717 3718 /* set last acccurve step */ 3719 data_lsb_set (&dev->init_regs[0xe1], 0x2af8, 3); 3720 3721 /* set msi 0x02 */ 3722 dev->init_regs[0xda] = 0x02; 3723 data_bitset (&dev->init_regs[0xdd], 0x03, 0); /*------xx*/ 3724 3725 /* set binary threshold high and low in little endian */ 3726 data_lsb_set (&dev->init_regs[0x19e], binarythresholdl, 2); 3727 data_lsb_set (&dev->init_regs[0x1a0], binarythresholdh, 2); 3728 3729 3730 data_bitset (&dev->init_regs[0x01], 0x08, 0); /*----x---*/ 3731 data_bitset (&dev->init_regs[0x16f], 0x40, 0); /*-x------*/ 3732 dev->init_regs[0x0bf] = (dev->init_regs[0x00bf] & 0xe0) | 0x20; 3733 dev->init_regs[0x163] = (dev->init_regs[0x0163] & 0x3f) | 0x40; 3734 3735 data_bitset (&dev->init_regs[0xd6], 0x0f, 8); /*----xxxx*/ 3736 data_bitset (&dev->init_regs[0x164], 0x80, 1); /*x------- */ 3737 3738 dev->init_regs[0x0bc] = 0x00; 3739 dev->init_regs[0x0bd] = 0x00; 3740 3741 dev->init_regs[0x165] = (dev->init_regs[0x0165] & 0x3f) | 0x80; 3742 dev->init_regs[0x0ed] = 0x10; 3743 dev->init_regs[0x0be] = 0x00; 3744 dev->init_regs[0x0d5] = 0x00; 3745 3746 dev->init_regs[0xee] = 0x00; 3747 dev->init_regs[0xef] = 0x00; 3748 dev->init_regs[0xde] = 0xff; 3749 3750 /* set bit[4] has_curves = 0 | bit[0..3] unknown = 0 */ 3751 data_bitset (&dev->init_regs[0xdf], 0x10, 0); /*---x----*/ 3752 data_bitset (&dev->init_regs[0xdf], 0x0f, 0); /*----xxxx*/ 3753 3754 /* Set motor type */ 3755 data_bitset (&dev->init_regs[0xd7], 0x80, dev->motorcfg->type); /*x------- */ 3756 3757 if (dev->motorcfg->type == MT_ONCHIP_PWM) 3758 { 3759 data_bitset (&dev->init_regs[0x14e], 0x10, 1); /*---x----*/ 3760 3761 /* set motorpwmfrequency */ 3762 data_bitset (&dev->init_regs[0xd7], 0x3f, dev->motorcfg->pwmfrequency); /*--xxxxxx*/ 3763 } 3764 3765 dev->init_regs[0x600] &= 0xfb; 3766 dev->init_regs[0x1d8] |= 0x08; 3767 3768 v160c_block_size = 0x04; 3769 mem_total = 0x80000; 3770 3771 /* check and setup installed ram */ 3772 RTS_DMA_CheckType (dev, dev->init_regs); 3773 rst = RTS_DMA_WaitReady (dev, 1500); 3774 3775 DBG (DBG_FNC, "- Init_Registers: %i\n", rst); 3776 3777 return rst; 3778} 3779 3780static SANE_Int 3781Read_FE3E (struct st_device *dev, SANE_Byte * destino) 3782{ 3783 SANE_Int rst; 3784 3785 DBG (DBG_FNC, "+ Read_FE3E:\n"); 3786 3787 rst = ERROR; 3788 if (destino != NULL) 3789 { 3790 SANE_Byte data; 3791 if (Read_Byte (dev->usb_handle, 0xfe3e, &data) == 0) 3792 { 3793 *destino = data; 3794 rst = OK; 3795 DBG (DBG_FNC, " -> %02x\n", _B0 (data)); 3796 } 3797 } 3798 3799 DBG (DBG_FNC, "- Read_FE3E: %i\n", rst); 3800 3801 return rst; 3802} 3803 3804static SANE_Int 3805Head_IsAtHome (struct st_device *dev, SANE_Byte * Regs) 3806{ 3807 SANE_Int rst; 3808 3809 DBG (DBG_FNC, "+ Head_IsAtHome:\n"); 3810 3811 /* if returns TRUE, lamp is at home. Otherwise it returns FALSE */ 3812 rst = 0; 3813 3814 if (Regs != NULL) 3815 { 3816 SANE_Byte data; 3817 if (Read_Byte (dev->usb_handle, 0xe96f, &data) == OK) 3818 { 3819 Regs[0x16f] = _B0 (data); 3820 rst = (data >> 6) & 1; 3821 } 3822 } 3823 3824 rst = (rst == 1) ? TRUE : FALSE; 3825 3826 DBG (DBG_FNC, "- Head_IsAtHome: %s\n", (rst == TRUE) ? "Yes" : "No"); 3827 3828 return rst; 3829} 3830 3831static SANE_Byte 3832RTS_IsExecuting (struct st_device *dev, SANE_Byte * Regs) 3833{ 3834 SANE_Byte rst; 3835 3836 DBG (DBG_FNC, "+ RTS_IsExecuting:\n"); 3837 3838 rst = 0; 3839 3840 if (Regs != NULL) 3841 { 3842 SANE_Byte data; 3843 if (Read_Byte (dev->usb_handle, 0xe800, &data) == OK) 3844 { 3845 Regs[0x00] = data; 3846 rst = (data >> 7) & 1; 3847 } 3848 } 3849 3850 DBG (DBG_FNC, "- RTS_IsExecuting: %i\n", rst); 3851 3852 return rst; 3853} 3854 3855static SANE_Int 3856RTS_WaitScanEnd (struct st_device *dev, SANE_Int msecs) 3857{ 3858 SANE_Byte data; 3859 SANE_Int rst; 3860 3861 DBG (DBG_FNC, "+ RTS_WaitScanEnd(msecs=%i):\n", msecs); 3862 3863 /* returns 0 if ok or timeout 3864 returns -1 if fails */ 3865 3866 rst = ERROR; 3867 3868 if (Read_Byte (dev->usb_handle, 0xe800, &data) == OK) 3869 { 3870 long ticks = GetTickCount () + msecs; 3871 rst = OK; 3872 while (((data & 0x80) != 0) && (ticks > GetTickCount ()) && (rst == OK)) 3873 { 3874 rst = Read_Byte (dev->usb_handle, 0xe800, &data); 3875 } 3876 } 3877 3878 DBG (DBG_FNC, "- RTS_WaitScanEnd: Ending with rst=%i\n", rst); 3879 3880 return rst; 3881} 3882 3883static SANE_Int 3884RTS_Enable_CCD (struct st_device *dev, SANE_Byte * Regs, SANE_Int channels) 3885{ 3886 SANE_Int rst = ERROR; 3887 3888 DBG (DBG_FNC, "+ RTS_Enable_CCD(*Regs, arg2=%i):\n", channels); 3889 3890 if (Read_Buffer (dev->usb_handle, 0xe810, &Regs[0x10], 4) == OK) 3891 { 3892 data_bitset (&Regs[0x10], 0xe0, channels); /*xxx----- */ 3893 data_bitset (&Regs[0x13], 0x80, channels >> 3); /*x------- */ 3894 3895 Write_Buffer (dev->usb_handle, 0xe810, &Regs[0x10], 4); 3896 rst = OK; 3897 } 3898 3899 DBG (DBG_FNC, "- RTS_Enable_CCD: %i\n", rst); 3900 3901 return rst; 3902} 3903 3904static SANE_Int 3905RTS_Warm_Reset (struct st_device *dev) 3906{ 3907 SANE_Byte data; 3908 SANE_Int rst; 3909 3910 DBG (DBG_FNC, "+ RTS_Warm_Reset:\n"); 3911 3912 rst = ERROR; 3913 if (Read_Byte (dev->usb_handle, 0xe800, &data) == OK) 3914 { 3915 data = (data & 0x3f) | 0x40; /*01------ */ 3916 if (Write_Byte (dev->usb_handle, 0xe800, data) == OK) 3917 { 3918 data &= 0xbf; /*-0------*/ 3919 rst = Write_Byte (dev->usb_handle, 0xe800, data); 3920 } 3921 } 3922 3923 DBG (DBG_FNC, "- RTS_Warm_Reset: %i\n", rst); 3924 3925 return rst; 3926} 3927 3928static SANE_Int 3929Lamp_Status_Timer_Set (struct st_device *dev, SANE_Int minutes) 3930{ 3931 SANE_Byte MyBuffer[2]; 3932 SANE_Int rst; 3933 3934 DBG (DBG_FNC, "+ Lamp_Status_Timer_Set(minutes=%i):\n", minutes); 3935 3936 MyBuffer[0] = dev->init_regs[0x0146] & 0xef; 3937 MyBuffer[1] = dev->init_regs[0x0147]; 3938 3939 if (minutes > 0) 3940 { 3941 double rst, op2; 3942 3943 minutes = _B0 (minutes); 3944 op2 = 2.682163611980331; 3945 MyBuffer[0x00] |= 0x10; 3946 rst = (minutes * op2); 3947 MyBuffer[0x01] = (SANE_Byte) floor (rst); 3948 } 3949 3950 dev->init_regs[0x147] = MyBuffer[1]; 3951 dev->init_regs[0x146] = 3952 (dev->init_regs[0x146] & 0xef) | (MyBuffer[0] & 0x10); 3953 3954 rst = 3955 Write_Word (dev->usb_handle, 0xe946, 3956 (SANE_Int) ((MyBuffer[1] << 8) + MyBuffer[0])); 3957 3958 DBG (DBG_FNC, "- Lamp_Status_Timer_Set: %i\n", rst); 3959 3960 return rst; 3961} 3962 3963static SANE_Int 3964Buttons_Enable (struct st_device *dev) 3965{ 3966 SANE_Int data, rst; 3967 3968 DBG (DBG_FNC, "+ Buttons_Enable:\n"); 3969 3970 if (Read_Word (dev->usb_handle, 0xe958, &data) == OK) 3971 { 3972 data |= 0x0f; 3973 rst = Write_Word (dev->usb_handle, 0xe958, data); 3974 } 3975 else 3976 rst = ERROR; 3977 3978 DBG (DBG_FNC, "- Buttons_Enable: %i\n", rst); 3979 3980 return rst; 3981} 3982 3983static SANE_Int 3984Buttons_Count (struct st_device *dev) 3985{ 3986 SANE_Int rst = 0; 3987 3988 /* This chipset supports up to six buttons */ 3989 3990 if (dev->buttons != NULL) 3991 rst = dev->buttons->count; 3992 3993 DBG (DBG_FNC, "> Buttons_Count: %i\n", rst); 3994 3995 return rst; 3996} 3997 3998static SANE_Int 3999Buttons_Status (struct st_device *dev) 4000{ 4001 SANE_Int rst = -1; 4002 SANE_Byte data; 4003 4004 DBG (DBG_FNC, "+ Buttons_Status\n"); 4005 4006 /* Each bit is 1 if button is not pressed, and 0 if it is pressed 4007 This chipset supports up to six buttons */ 4008 4009 if (Read_Byte (dev->usb_handle, 0xe968, &data) == OK) 4010 rst = _B0 (data); 4011 4012 DBG (DBG_FNC, "- Buttons_Status: %i\n", rst); 4013 4014 return rst; 4015} 4016 4017static SANE_Int 4018Buttons_Released (struct st_device *dev) 4019{ 4020 SANE_Int rst = -1; 4021 SANE_Byte data; 4022 4023 DBG (DBG_FNC, "+ Buttons_Released\n"); 4024 4025 /* Each bit is 1 if button is released, until reading this register. Then 4026 entire register is cleared. This chipset supports up to six buttons */ 4027 4028 if (Read_Byte (dev->usb_handle, 0xe96a, &data) == OK) 4029 rst = _B0 (data); 4030 4031 DBG (DBG_FNC, "- Buttons_Released: %i\n", rst); 4032 4033 return rst; 4034} 4035 4036static SANE_Int 4037Buttons_Order (struct st_device *dev, SANE_Int mask) 4038{ 4039 /* this is a way to order each button according to its bit in register 0xe968 */ 4040 SANE_Int rst = -1; 4041 4042 if (dev->buttons != NULL) 4043 { 4044 SANE_Int a; 4045 4046 for (a = 0; a < 6; a++) 4047 { 4048 if (dev->buttons->mask[a] == mask) 4049 { 4050 rst = a; 4051 break; 4052 } 4053 } 4054 } 4055 4056 return rst; 4057} 4058 4059static SANE_Int 4060GainOffset_Clear (struct st_device *dev) 4061{ 4062 SANE_Int rst = OK; 4063 4064 DBG (DBG_FNC, "+ GainOffset_Clear:\n"); 4065 4066 /* clear offsets */ 4067 offset[CL_RED] = offset[CL_GREEN] = offset[CL_BLUE] = 0; 4068 4069 /* save offsets */ 4070 /* check if chipset supports accessing eeprom */ 4071 if ((dev->chipset->capabilities & CAP_EEPROM) != 0) 4072 { 4073 SANE_Int a; 4074 4075 for (a = CL_RED; a <= CL_BLUE; a++) 4076 RTS_EEPROM_WriteWord (dev->usb_handle, 0x70 + (2 * a), 0); 4077 4078 /* update checksum */ 4079 rst = RTS_EEPROM_WriteByte (dev->usb_handle, 0x76, 0); 4080 } 4081 4082 DBG (DBG_FNC, "- GainOffset_Clear: %i\n", rst); 4083 4084 return rst; 4085} 4086 4087static SANE_Int 4088Lamp_Status_Get (struct st_device *dev, SANE_Byte * flb_lamp, 4089 SANE_Byte * tma_lamp) 4090{ 4091 /* The only reason that I think windows driver uses two variables to get 4092 which lamp is switched on instead of one variable is that some chipset 4093 model could have both lamps switched on, so I'm maintaining such var */ 4094 4095 SANE_Int rst = ERROR; /* default */ 4096 4097 DBG (DBG_FNC, "+ Lamp_Status_Get:\n"); 4098 4099 if ((flb_lamp != NULL) && (tma_lamp != NULL)) 4100 { 4101 SANE_Int data1; 4102 SANE_Byte data2; 4103 4104 if (Read_Byte (dev->usb_handle, 0xe946, &data2) == OK) 4105 { 4106 if (Read_Word (dev->usb_handle, 0xe954, &data1) == OK) 4107 { 4108 rst = OK; 4109 4110 *flb_lamp = 0; 4111 *tma_lamp = 0; 4112 4113 switch (dev->chipset->model) 4114 { 4115 case RTS8822BL_03A: 4116 *flb_lamp = ((data2 & 0x40) != 0) ? 1 : 0; 4117 *tma_lamp = (((data2 & 0x20) != 0) 4118 && ((data1 & 0x10) != 0)) ? 1 : 0; 4119 break; 4120 default: 4121 if ((_B1 (data1) & 0x10) == 0) 4122 *flb_lamp = (data2 >> 6) & 1; 4123 else 4124 *tma_lamp = (data2 >> 6) & 1; 4125 break; 4126 } 4127 } 4128 } 4129 } 4130 4131 DBG (DBG_FNC, "- Lamp_Status_Get: rst=%i flb=%i tma=%i\n", rst, 4132 _B0 (*flb_lamp), _B0 (*tma_lamp)); 4133 4134 return rst; 4135} 4136 4137static SANE_Int 4138RTS_DMA_WaitReady (struct st_device *dev, SANE_Int msecs) 4139{ 4140 SANE_Byte data; 4141 SANE_Int rst; 4142 long mytime; 4143 4144 DBG (DBG_FNC, "+ RTS_DMA_WaitReady(msecs=%i):\n", msecs); 4145 4146 rst = OK; 4147 mytime = GetTickCount () + msecs; 4148 4149 while ((mytime > GetTickCount ()) && (rst == OK)) 4150 { 4151 if (Read_Byte (dev->usb_handle, 0xef09, &data) == OK) 4152 { 4153 if ((data & 1) == 0) 4154 usleep (1000 * 100); 4155 else 4156 break; 4157 } 4158 else 4159 rst = ERROR; 4160 } 4161 4162 DBG (DBG_FNC, "- RTS_DMA_WaitReady: %i\n", rst); 4163 4164 return rst; 4165} 4166 4167static SANE_Int 4168RTS_WaitInitEnd (struct st_device *dev, SANE_Int msecs) 4169{ 4170 SANE_Byte data; 4171 SANE_Int rst; 4172 long mytime; 4173 4174 DBG (DBG_FNC, "+ RTS_WaitInitEnd(msecs=%i):\n", msecs); 4175 4176 rst = OK; 4177 mytime = GetTickCount () + msecs; 4178 4179 while ((mytime > GetTickCount ()) && (rst == OK)) 4180 { 4181 if (Read_Byte (dev->usb_handle, 0xf910, &data) == OK) 4182 { 4183 if ((data & 8) == 0) 4184 usleep (1000 * 100); 4185 else 4186 break; 4187 } 4188 else 4189 rst = ERROR; 4190 } 4191 4192 DBG (DBG_FNC, "- RTS_WaitInitEnd: %i\n", rst); 4193 4194 return rst; 4195} 4196 4197static SANE_Int 4198Motor_Change (struct st_device *dev, SANE_Byte * buffer, SANE_Byte value) 4199{ 4200 SANE_Int data, rst; 4201 4202 DBG (DBG_FNC, "+ Motor_Change(*buffer, value=%i):\n", value); 4203 4204 if (Read_Word (dev->usb_handle, 0xe954, &data) == OK) 4205 { 4206 data &= 0xcf; /*--00----*/ 4207 value--; 4208 switch (value) 4209 { 4210 case 2: 4211 data |= 0x30; 4212 break; /*--11----*/ 4213 case 1: 4214 data |= 0x20; 4215 break; /*--10----*/ 4216 case 0: 4217 data |= 0x10; 4218 break; /*--01----*/ 4219 } 4220 4221 buffer[0x154] = _B0 (data); 4222 4223 rst = Write_Byte (dev->usb_handle, 0xe954, buffer[0x154]); 4224 } 4225 else 4226 rst = ERROR; 4227 4228 DBG (DBG_FNC, "- Motor_Change: %i\n", rst); 4229 4230 return rst; 4231} 4232 4233static SANE_Int 4234RTS_DMA_Read (struct st_device *dev, SANE_Int dmacs, SANE_Int options, 4235 SANE_Int size, SANE_Byte * buffer) 4236{ 4237 SANE_Int rst = ERROR; 4238 4239 DBG (DBG_FNC, 4240 "+ RTS_DMA_Read(dmacs=%04x, options=%04x, size=%i., *buffer):\n", 4241 dmacs, options, size); 4242 4243 /* is there any buffer to send? */ 4244 if ((buffer != NULL) && (size > 0)) 4245 { 4246 /* reset dma */ 4247 if (RTS_DMA_Reset (dev) == OK) 4248 { 4249 /* prepare dma to read */ 4250 if (RTS_DMA_Enable_Read (dev, dmacs, size, options) == OK) 4251 { 4252 SANE_Int transferred; 4253 4254 rst = 4255 Bulk_Operation (dev, BLK_READ, size, buffer, &transferred); 4256 } 4257 } 4258 } 4259 4260 DBG (DBG_FNC, "- RTS_DMA_Read(): %i\n", rst); 4261 4262 return rst; 4263} 4264 4265static SANE_Int 4266RTS_DMA_Write (struct st_device *dev, SANE_Int dmacs, SANE_Int options, 4267 SANE_Int size, SANE_Byte * buffer) 4268{ 4269 SANE_Int rst = ERROR; 4270 4271 DBG (DBG_FNC, 4272 "+ RTS_DMA_Write(dmacs=%04x, options=%04x, size=%i., *buffer):\n", 4273 dmacs, options, size); 4274 4275 /* is there any buffer to send? */ 4276 if ((buffer != NULL) && (size > 0)) 4277 { 4278 /* reset dma */ 4279 if (RTS_DMA_Reset (dev) == OK) 4280 { 4281 /* prepare dma to write */ 4282 if (RTS_DMA_Enable_Write (dev, dmacs, size, options) == OK) 4283 { 4284 SANE_Int transferred; 4285 SANE_Byte *check_buffer; 4286 4287 check_buffer = (SANE_Byte *) malloc (size); 4288 if (check_buffer != NULL) 4289 { 4290 /* if some transfer fails we try again until ten times */ 4291 SANE_Int a; 4292 for (a = 10; a > 0; a--) 4293 { 4294 /* send buffer */ 4295 Bulk_Operation (dev, BLK_WRITE, size, buffer, 4296 &transferred); 4297 4298 /* prepare dma to read */ 4299 if (RTS_DMA_Enable_Read (dev, dmacs, size, options) == 4300 OK) 4301 { 4302 SANE_Int b = 0, diff = FALSE; 4303 4304 /* read buffer */ 4305 Bulk_Operation (dev, BLK_READ, size, check_buffer, 4306 &transferred); 4307 4308 /* check buffers */ 4309 while ((b < size) && (diff == FALSE)) 4310 { 4311 if (buffer[b] == check_buffer[b]) 4312 b++; 4313 else 4314 diff = TRUE; 4315 } 4316 4317 /* if buffers are equal we can break loop */ 4318 if (diff == TRUE) 4319 { 4320 /* cancel dma */ 4321 RTS_DMA_Cancel (dev); 4322 4323 /* prepare dma to write buffer again */ 4324 if (RTS_DMA_Enable_Write 4325 (dev, dmacs, size, options) != OK) 4326 break; 4327 } 4328 else 4329 { 4330 /* everything went ok */ 4331 rst = OK; 4332 break; 4333 } 4334 } 4335 else 4336 break; 4337 } 4338 4339 /* free check buffer */ 4340 free (check_buffer); 4341 } 4342 else 4343 { 4344 /* for some reason it's not possible to allocate space to check 4345 sent buffer so we just write data */ 4346 Bulk_Operation (dev, BLK_WRITE, size, buffer, &transferred); 4347 rst = OK; 4348 } 4349 } 4350 } 4351 } 4352 4353 DBG (DBG_FNC, "- RTS_DMA_Write(): %i\n", rst); 4354 4355 return rst; 4356} 4357 4358static SANE_Int 4359RTS_DMA_CheckType (struct st_device *dev, SANE_Byte * Regs) 4360{ 4361 /* This function tries to detect what kind of RAM supports chipset */ 4362 /* Returns a value between 0 and 4. -1 means error */ 4363 4364 SANE_Int rst = -1; 4365 4366 DBG (DBG_FNC, "+ RTS_DMA_CheckType(*Regs):\n"); 4367 4368 if (Regs != NULL) 4369 { 4370 SANE_Byte *out_buffer; 4371 4372 /* define buffer to send */ 4373 out_buffer = (SANE_Byte *) malloc (sizeof (SANE_Byte) * 2072); 4374 if (out_buffer != NULL) 4375 { 4376 SANE_Byte *in_buffer; 4377 4378 /* define incoming buffer */ 4379 in_buffer = (SANE_Byte *) malloc (sizeof (SANE_Byte) * 2072); 4380 if (in_buffer != NULL) 4381 { 4382 SANE_Int a, b, diff; 4383 4384 /* fill outgoing buffer with a known pattern */ 4385 b = 0; 4386 for (a = 0; a < 2072; a++) 4387 { 4388 out_buffer[a] = b; 4389 b++; 4390 if (b == 0x61) 4391 b = 0; 4392 } 4393 4394 /* let's send buffer with different ram types and compare 4395 incoming buffer until getting the right type */ 4396 4397 for (a = 4; a >= 0; a--) 4398 { 4399 /* set ram type */ 4400 if (RTS_DMA_SetType (dev, Regs, a) != OK) 4401 break; 4402 4403 /* wait 1500 milliseconds */ 4404 if (RTS_DMA_WaitReady (dev, 1500) == OK) 4405 { 4406 /* reset dma */ 4407 RTS_DMA_Reset (dev); 4408 4409 /* write buffer */ 4410 RTS_DMA_Write (dev, 0x0004, 0x102, 2072, out_buffer); 4411 4412 /* now read buffer */ 4413 RTS_DMA_Read (dev, 0x0004, 0x102, 2072, in_buffer); 4414 4415 /* check buffers */ 4416 b = 0; 4417 diff = FALSE; 4418 while ((b < 2072) && (diff == FALSE)) 4419 { 4420 if (out_buffer[b] == in_buffer[b]) 4421 b++; 4422 else 4423 diff = TRUE; 4424 } 4425 4426 /* if buffers are equal */ 4427 if (diff == FALSE) 4428 { 4429 SANE_Int data = 0; 4430 4431 /* buffers are equal so we've found the right ram type */ 4432 memset (out_buffer, 0, 0x20); 4433 for (b = 0; b < 0x20; b += 2) 4434 out_buffer[b] = b; 4435 4436 /* write buffer */ 4437 if (RTS_DMA_Write 4438 (dev, 0x0004, 0x0000, 0x20, out_buffer) == OK) 4439 { 4440 SANE_Int c = 0; 4441 diff = TRUE; 4442 4443 do 4444 { 4445 c++; 4446 for (b = 1; b < 0x20; b += 2) 4447 out_buffer[b] = c; 4448 4449 if (RTS_DMA_Write 4450 (dev, 0x0004, (_B0 (c) << 0x11) >> 0x04, 4451 0x20, out_buffer) == OK) 4452 { 4453 if (RTS_DMA_Read 4454 (dev, 0x0004, 0x0000, 0x20, 4455 in_buffer) == OK) 4456 { 4457 b = 0; 4458 diff = FALSE; 4459 while ((b < 0x20) 4460 && (diff == FALSE)) 4461 { 4462 if (out_buffer[b] == 4463 in_buffer[b]) 4464 b++; 4465 else 4466 diff = TRUE; 4467 } 4468 4469 if (diff == FALSE) 4470 data = c << 7; 4471 } 4472 } 4473 } 4474 while ((c < 0x80) && (diff == TRUE)); 4475 } 4476 4477 switch (data) 4478 { 4479 case 16384: 4480 Regs[0x708] &= 0x1f; 4481 Regs[0x708] |= 0x80; 4482 break; 4483 case 8192: 4484 Regs[0x708] &= 0x1f; 4485 Regs[0x708] |= 0x60; 4486 break; 4487 case 4096: 4488 Regs[0x708] &= 0x1f; 4489 Regs[0x708] |= 0x40; 4490 break; 4491 case 2048: 4492 Regs[0x708] &= 0x1f; 4493 Regs[0x708] |= 0x20; 4494 break; 4495 case 1024: 4496 Regs[0x708] &= 0x1f; 4497 data = 0x200; 4498 break; 4499 case 128: 4500 Regs[0x708] &= 0x1f; 4501 break; 4502 } 4503 4504 DBG (DBG_FNC, " -> data1 = 0x%08x\n", 4505 (data * 4) * 1024); 4506 DBG (DBG_FNC, " -> data2 = 0x%08x\n", data * 1024); 4507 DBG (DBG_FNC, " -> type = 0x%04x\n", 4508 Regs[0x708] >> 5); 4509 4510 RTS_DMA_SetType (dev, Regs, Regs[0x708] >> 5); 4511 4512 rst = OK; 4513 break; 4514 } 4515 } 4516 else 4517 break; 4518 } 4519 4520 free (in_buffer); 4521 } 4522 4523 free (out_buffer); 4524 } 4525 } 4526 4527 DBG (DBG_FNC, "- RTS_DMA_CheckType(): %i\n", rst); 4528 4529 return rst; 4530} 4531 4532static SANE_Int 4533RTS_DMA_SetType (struct st_device *dev, SANE_Byte * Regs, SANE_Byte ramtype) 4534{ 4535 SANE_Int rst = ERROR; 4536 4537 DBG (DBG_FNC, "+ RTS_DMA_SetType(*Regs, ramtype=%i):\n", ramtype); 4538 4539 if (Regs != NULL) 4540 { 4541 data_bitset (&Regs[0x708], 0x08, 0); /*----0---*/ 4542 4543 if (Write_Byte (dev->usb_handle, 0xef08, Regs[0x708]) == OK) 4544 { 4545 data_bitset (&Regs[0x708], 0xe0, ramtype); 4546 4547 if (Write_Byte (dev->usb_handle, 0xef08, Regs[0x708]) == OK) 4548 { 4549 data_bitset (&Regs[0x708], 0x08, 1); /*----1---*/ 4550 rst = Write_Byte (dev->usb_handle, 0xef08, Regs[0x708]); 4551 } 4552 } 4553 } 4554 4555 DBG (DBG_FNC, "- RTS_DMA_SetType: %i\n", rst); 4556 4557 return rst; 4558} 4559 4560static void 4561Motor_Release (struct st_device *dev) 4562{ 4563 SANE_Byte data = 0; 4564 4565 DBG (DBG_FNC, "+ Motor_Release:\n"); 4566 4567 if (Read_Byte (dev->usb_handle, 0xe8d9, &data) == OK) 4568 { 4569 data |= 4; 4570 Write_Byte (dev->usb_handle, 0xe8d9, data); 4571 } 4572 4573 DBG (DBG_FNC, "- Motor_Release:\n"); 4574} 4575 4576static SANE_Byte 4577GainOffset_Counter_Load (struct st_device *dev) 4578{ 4579 SANE_Byte data = 0x0f; 4580 4581 DBG (DBG_FNC, "+ GainOffset_Counter_Load:\n"); 4582 4583 /* check if chipset supports accessing eeprom */ 4584 if ((dev->chipset->capabilities & CAP_EEPROM) != 0) 4585 if (RTS_EEPROM_ReadByte (dev->usb_handle, 0x77, &data) != OK) 4586 data = 0x0f; 4587 4588 DBG (DBG_FNC, "- GainOffset_Counter_Load: %i\n", _B0 (data)); 4589 4590 return data; 4591} 4592 4593static SANE_Int 4594RTS_Execute (struct st_device *dev) 4595{ 4596 SANE_Byte e813, e800; 4597 SANE_Int ret; 4598 4599 DBG (DBG_FNC, "+ RTS_Execute:\n"); 4600 4601 e813 = 0; 4602 e800 = 0; 4603 ret = ERROR; 4604 4605 if (Read_Byte (dev->usb_handle, 0xe800, &e800) == OK) 4606 { 4607 if (Read_Byte (dev->usb_handle, 0xe813, &e813) == OK) 4608 { 4609 e813 &= 0xbf; 4610 if (Write_Byte (dev->usb_handle, 0xe813, e813) == OK) 4611 { 4612 e800 |= 0x40; 4613 if (Write_Byte (dev->usb_handle, 0xe800, e800) == OK) 4614 { 4615 e813 |= 0x40; 4616 if (Write_Byte (dev->usb_handle, 0xe813, e813) == OK) 4617 { 4618 e800 &= 0xbf; 4619 if (Write_Byte (dev->usb_handle, 0xe800, e800) == OK) 4620 { 4621 usleep (1000 * 100); 4622 e800 |= 0x80; 4623 ret = Write_Byte (dev->usb_handle, 0xe800, e800); 4624 } 4625 } 4626 } 4627 } 4628 } 4629 } 4630 4631 DBG (DBG_FNC, "- RTS_Execute: %i\n", ret); 4632 4633 return ret; 4634} 4635 4636static SANE_Int 4637RTS_isTmaAttached (struct st_device *dev) 4638{ 4639 SANE_Int rst; 4640 4641 DBG (DBG_FNC, "+ RTS_isTmaAttached:\n"); 4642 4643 /* returns 0 if Tma is attached. Otherwise 1 */ 4644 if (Read_Word (dev->usb_handle, 0xe968, &rst) == OK) 4645 { 4646 rst = ((_B1 (rst) & 2) != 0) ? FALSE : TRUE; 4647 } 4648 else 4649 rst = TRUE; 4650 4651 DBG (DBG_FNC, "- RTS_isTmaAttached: %s\n", (rst == TRUE) ? "Yes" : "No"); 4652 4653 return rst; 4654} 4655 4656static SANE_Int 4657Gamma_AllocTable (SANE_Byte * table) 4658{ 4659 SANE_Int C; 4660 SANE_Int rst = OK; 4661 4662 hp_gamma->depth = 8; 4663 4664 for (C = 0; C < 3; C++) 4665 if (hp_gamma->table[C] == NULL) 4666 hp_gamma->table[C] = malloc (sizeof (SANE_Byte) * 256); 4667 4668 if ((hp_gamma->table[CL_RED] != NULL) && 4669 (hp_gamma->table[CL_GREEN] != NULL) && 4670 (hp_gamma->table[CL_BLUE] != NULL)) 4671 { 4672 /* All tables allocated */ 4673 for (C = 0; C < 256; C++) 4674 { 4675 if ((table != NULL) && (RTS_Debug->EnableGamma == TRUE)) 4676 { 4677 /* fill gamma tables with user defined values */ 4678 hp_gamma->table[CL_RED][C] = table[C]; 4679 hp_gamma->table[CL_GREEN][C] = table[0x100 + C]; 4680 hp_gamma->table[CL_BLUE][C] = table[0x200 + C]; 4681 } 4682 else 4683 { 4684 hp_gamma->table[CL_RED][C] = C; 4685 hp_gamma->table[CL_GREEN][C] = C; 4686 hp_gamma->table[CL_BLUE][C] = C; 4687 } 4688 } 4689 4690 /* Locate threshold of bw */ 4691 for (C = 0; C < 256; C++) 4692 if (hp_gamma->table[CL_RED][C] != 0) 4693 break; 4694 4695 bw_threshold = C - 1; 4696 } 4697 else 4698 { 4699 /* Some alloc failed */ 4700 rst = ERROR; 4701 4702 Gamma_FreeTables (); 4703 } 4704 4705 DBG (DBG_FNC, "> Gamma_AllocTable: %i >> bw_threshold = %i\n", rst, 4706 bw_threshold); 4707 4708 return rst; 4709} 4710 4711static SANE_Int 4712Gamma_Apply (struct st_device *dev, SANE_Byte * Regs, 4713 struct st_scanparams *scancfg, struct st_hwdconfig *hwdcfg, 4714 struct st_gammatables *mygamma) 4715{ 4716 SANE_Int rst = OK; 4717 4718 DBG (DBG_FNC, "+ Gamma_Apply(*Regs, *scancfg, *hwdcfg, *mygamma):\n"); 4719 dbg_ScanParams (scancfg); 4720 4721 if (hwdcfg->use_gamma_tables == FALSE) 4722 { 4723 DBG (DBG_FNC, "-> Gamma tables are not used\n"); 4724 4725 v1600 = NULL; 4726 v1604 = NULL; 4727 v1608 = NULL; 4728 } 4729 else 4730 { 4731 /*390b */ 4732 SANE_Int table_size, buffersize, c; 4733 SANE_Byte channels, *gammabuffer; 4734 4735 DBG (DBG_FNC, "-> Using gamma tables\n"); 4736 4737 /* get channels count */ 4738 channels = 3; /* default */ 4739 4740 if (scancfg->colormode != CM_COLOR) 4741 { 4742 if (scancfg->channel != 3) 4743 { 4744 if (scancfg->colormode != 3) 4745 channels = (scancfg->samplerate == PIXEL_RATE) ? 2 : 1; 4746 } 4747 } 4748 4749 /* get size for gamma tables */ 4750 switch (mygamma->depth & 0x0c) 4751 { 4752 case 0: 4753 table_size = 0x100 + (mygamma->depth & 1); 4754 break; 4755 case 4: 4756 table_size = 0x400 + (mygamma->depth & 1); 4757 break; 4758 case 8: 4759 table_size = 0x1000 + (mygamma->depth & 1); 4760 break; 4761 default: 4762 table_size = 2; 4763 break; 4764 } 4765 4766 /* allocate space for gamma buffer */ 4767 buffersize = table_size * channels; 4768 gammabuffer = (SANE_Byte *) malloc (buffersize * sizeof (SANE_Byte)); 4769 if (gammabuffer != NULL) 4770 { 4771 /* update gamma pointers for each channel */ 4772 v1600 = (SANE_Byte *) & mygamma->table[CL_RED]; 4773 v1604 = (SANE_Byte *) & mygamma->table[CL_GREEN]; 4774 v1608 = (SANE_Byte *) & mygamma->table[CL_BLUE]; 4775 4776 /* include gamma tables into one buffer */ 4777 for (c = 0; c < channels; c++) 4778 memcpy (gammabuffer + (c * table_size), mygamma->table[c], 4779 table_size); 4780 4781 /* send gamma buffer to scanner */ 4782 Write_Byte (dev->usb_handle, 0xee0b, Regs[0x060b] & 0xaf); 4783 rst = Gamma_SendTables (dev, Regs, gammabuffer, buffersize); 4784 Write_Byte (dev->usb_handle, 0xee0b, Regs[0x060b]); 4785 4786 /* free gamma buffer */ 4787 free (gammabuffer); 4788 } 4789 else 4790 rst = ERROR; 4791 } 4792 4793 return rst; 4794} 4795 4796static SANE_Int 4797Refs_Analyze_Pattern (struct st_scanparams *scancfg, 4798 SANE_Byte * scanned_pattern, SANE_Int * ler1, 4799 SANE_Int ler1order, SANE_Int * ser1, SANE_Int ser1order) 4800{ 4801 SANE_Int buffersize, xpos, ypos, coord, cnt, chn_size, dist, rst; 4802 double *color_sum, *color_dif, diff_max; 4803 SANE_Int vector[3]; 4804 4805 DBG (DBG_FNC, 4806 "+ Refs_Analyze_Pattern(depth=%i, width=%i, height=%i, *scanned_pattern, *ler1, ler1order=%i, *ser1, ser1order=%i)\n", 4807 scancfg->depth, scancfg->coord.width, scancfg->coord.height, ler1order, 4808 ser1order); 4809 4810 rst = ERROR; /* by default */ 4811 dist = 5; /* distance to compare */ 4812 chn_size = (scancfg->depth > 8) ? 2 : 1; 4813 buffersize = max (scancfg->coord.width, scancfg->coord.height); 4814 4815 color_sum = (double *) malloc (sizeof (double) * buffersize); 4816 if (color_sum != NULL) 4817 { 4818 color_dif = (double *) malloc (sizeof (double) * buffersize); 4819 if (color_dif != NULL) 4820 { 4821 /*-------- 1st SER -------- */ 4822 coord = 1; 4823 4824 if ((scancfg->coord.width - dist) > 1) 4825 { 4826 /* clear buffers */ 4827 memset (color_sum, 0, sizeof (double) * buffersize); 4828 memset (color_dif, 0, sizeof (double) * buffersize); 4829 4830 for (xpos = 0; xpos < scancfg->coord.width; xpos++) 4831 { 4832 for (ypos = 0; ypos < 20; ypos++) 4833 color_sum[xpos] += 4834 data_lsb_get (scanned_pattern + 4835 (scancfg->coord.width * ypos) + xpos, 4836 chn_size); 4837 } 4838 4839 diff_max = 4840 (ser1order != 4841 0) ? color_sum[0] - color_sum[1] : color_sum[1] - 4842 color_sum[0]; 4843 color_dif[0] = diff_max; 4844 cnt = 1; 4845 4846 do 4847 { 4848 color_dif[cnt] = 4849 (ser1order != 4850 0) ? color_sum[cnt] - color_sum[cnt + 4851 dist] : color_sum[cnt + 4852 dist] - 4853 color_sum[cnt]; 4854 4855 if ((color_dif[cnt] >= 0) && (color_dif[cnt] > diff_max)) 4856 { 4857 /*d4df */ 4858 diff_max = color_dif[cnt]; 4859 if (fabs (color_dif[cnt] - color_dif[cnt - 1]) > 4860 fabs (color_dif[coord] - color_dif[coord - 1])) 4861 coord = cnt; 4862 } 4863 4864 cnt++; 4865 } 4866 while (cnt < (scancfg->coord.width - dist)); 4867 } 4868 4869 vector[0] = coord + dist; 4870 4871 /*-------- 1st LER -------- */ 4872 coord = 1; 4873 4874 if ((scancfg->coord.height - dist) > 1) 4875 { 4876 /* clear buffers */ 4877 memset (color_sum, 0, sizeof (double) * buffersize); 4878 memset (color_dif, 0, sizeof (double) * buffersize); 4879 4880 for (ypos = 0; ypos < scancfg->coord.height; ypos++) 4881 { 4882 for (xpos = vector[0]; xpos < scancfg->coord.width - dist; 4883 xpos++) 4884 color_sum[ypos] += 4885 data_lsb_get (scanned_pattern + 4886 (scancfg->coord.width * ypos) + xpos, 4887 chn_size); 4888 } 4889 4890 diff_max = 4891 (ler1order != 4892 0) ? color_sum[0] - color_sum[1] : color_sum[1] - 4893 color_sum[0]; 4894 color_dif[0] = diff_max; 4895 4896 cnt = 1; 4897 4898 do 4899 { 4900 color_dif[cnt] = 4901 (ler1order != 4902 0) ? color_sum[cnt] - color_sum[cnt + 4903 dist] : color_sum[cnt + 4904 dist] - 4905 color_sum[cnt]; 4906 4907 if ((color_dif[cnt] >= 0) && (color_dif[cnt] > diff_max)) 4908 { 4909 diff_max = color_dif[cnt]; 4910 if (fabs (color_dif[cnt] - color_dif[cnt - 1]) > 4911 fabs (color_dif[coord] - color_dif[coord - 1])) 4912 coord = cnt; 4913 } 4914 4915 cnt++; 4916 } 4917 while (cnt < (scancfg->coord.height - dist)); 4918 } 4919 4920 vector[1] = coord + dist; 4921 4922 /*-------- 1st LER -------- */ 4923 if ((scancfg->coord.width - dist) > 1) 4924 { 4925 /* clear buffers */ 4926 memset (color_sum, 0, sizeof (double) * buffersize); 4927 memset (color_dif, 0, sizeof (double) * buffersize); 4928 4929 for (xpos = 0; xpos < scancfg->coord.width; xpos++) 4930 { 4931 for (ypos = coord + 4; ypos < scancfg->coord.height; ypos++) 4932 color_sum[xpos] += 4933 data_lsb_get (scanned_pattern + 4934 (scancfg->coord.width * ypos) + xpos, 4935 chn_size); 4936 } 4937 4938 diff_max = 4939 (ser1order != 4940 0) ? color_sum[0] - color_sum[1] : color_sum[1] - 4941 color_sum[0]; 4942 color_dif[0] = diff_max; 4943 cnt = 1; 4944 4945 do 4946 { 4947 color_dif[cnt] = 4948 (ser1order != 4949 0) ? color_sum[cnt] - color_sum[cnt + 4950 dist] : color_sum[cnt + 4951 dist] - 4952 color_sum[cnt]; 4953 4954 if ((color_dif[cnt] >= 0) && (color_dif[cnt] > diff_max)) 4955 { 4956 diff_max = color_dif[cnt]; 4957 if (fabs (color_dif[cnt] - color_dif[cnt - 1]) > 4958 fabs (color_dif[coord] - color_dif[coord - 1])) 4959 coord = cnt; 4960 } 4961 4962 cnt++; 4963 } 4964 while (cnt < (scancfg->coord.width - dist)); 4965 } 4966 4967 vector[2] = coord + dist; 4968 4969 /* save image */ 4970 if (RTS_Debug->SaveCalibFile != FALSE) 4971 dbg_autoref (scancfg, scanned_pattern, vector[0], vector[2], 4972 vector[1]); 4973 4974 /* assign values detected */ 4975 if (ser1 != NULL) 4976 *ser1 = vector[2]; 4977 4978 if (ler1 != NULL) 4979 *ler1 = vector[1]; 4980 4981 /* show values */ 4982 DBG (DBG_FNC, " -> Vectors found: x1=%i, x2=%i, y=%i\n", vector[0], 4983 vector[2], vector[1]); 4984 4985 rst = OK; 4986 4987 free (color_dif); 4988 } 4989 4990 free (color_sum); 4991 } 4992 4993 DBG (DBG_FNC, "- Refs_Analyze_Pattern: %i\n", rst); 4994 4995 return rst; 4996} 4997 4998static double 4999get_shrd (double value, SANE_Int desp) 5000{ 5001 if (desp <= 0x40) 5002 return value / pow (2, desp); 5003 else 5004 return 0; 5005} 5006 5007static char 5008get_byte (double value) 5009{ 5010 unsigned int data; 5011 double temp; 5012 5013 if (value > 0xffffffff) 5014 { 5015 temp = floor (get_shrd (value, 0x20)); 5016 temp *= pow (2, 32); 5017 value -= temp; 5018 } 5019 5020 data = (unsigned int) value; 5021 5022 data = _B0 (data); 5023 5024 return data; 5025} 5026 5027static SANE_Int 5028Timing_SetLinearImageSensorClock (SANE_Byte * Regs, struct st_cph *cph) 5029{ 5030 SANE_Int rst = ERROR; 5031 5032 DBG (DBG_FNC, 5033 "+ Timing_SetLinearImageSensorClock(SANE_Byte *Regs, struct st_cph *cph)\n"); 5034 5035 dbg_sensorclock (cph); 5036 5037 if ((Regs != NULL) && (cph != NULL)) 5038 { 5039 Regs[0x00] = get_byte (cph->p1); 5040 Regs[0x01] = get_byte (get_shrd (cph->p1, 0x08)); 5041 Regs[0x02] = get_byte (get_shrd (cph->p1, 0x10)); 5042 Regs[0x03] = get_byte (get_shrd (cph->p1, 0x18)); 5043 5044 Regs[0x04] &= 0x80; 5045 Regs[0x04] |= ((get_byte (get_shrd (cph->p1, 0x20))) & 0x0f); 5046 Regs[0x04] |= ((cph->ps & 1) << 6); 5047 Regs[0x04] |= ((cph->ge & 1) << 5); 5048 Regs[0x04] |= ((cph->go & 1) << 4); 5049 5050 Regs[0x05] = get_byte (cph->p2); 5051 Regs[0x06] = get_byte (get_shrd (cph->p2, 0x08)); 5052 Regs[0x07] = get_byte (get_shrd (cph->p2, 0x10)); 5053 Regs[0x08] = get_byte (get_shrd (cph->p2, 0x18)); 5054 Regs[0x09] &= 0xf0; 5055 Regs[0x09] |= ((get_byte (get_shrd (cph->p2, 0x20))) & 0x0f); 5056 5057 rst = OK; 5058 } 5059 5060 DBG (DBG_FNC, "- Timing_SetLinearImageSensorClock: %i\n", rst); 5061 5062 return rst; 5063} 5064 5065static void 5066RTS_Setup_SensorTiming (struct st_device *dev, SANE_Int mytiming, 5067 SANE_Byte * Regs) 5068{ 5069 DBG (DBG_FNC, "+ RTS_Setup_SensorTiming(mytiming=%i, *Regs):\n", mytiming); 5070 5071 if ((Regs != NULL) && (mytiming < dev->timings_count)) 5072 { 5073 struct st_timing *mt = dev->timings[mytiming]; 5074 5075 if (mt != NULL) 5076 { 5077 dbg_timing (mt); 5078 5079 /* Correlated-Double-Sample 1 & 2 */ 5080 data_bitset (&Regs[0x92], 0x3f, mt->cdss[0]); 5081 data_bitset (&Regs[0x93], 0x3f, mt->cdsc[0]); 5082 data_bitset (&Regs[0x94], 0x3f, mt->cdss[1]); 5083 data_bitset (&Regs[0x95], 0x3f, mt->cdsc[1]); 5084 5085 data_bitset (&Regs[0x96], 0x3f, mt->cnpp); 5086 5087 /* Linear image sensor transfer gates */ 5088 data_bitset (&Regs[0x45], 0x80, mt->cvtrp[0]); 5089 data_bitset (&Regs[0x45], 0x40, mt->cvtrp[1]); 5090 data_bitset (&Regs[0x45], 0x20, mt->cvtrp[2]); 5091 5092 data_bitset (&Regs[0x45], 0x1f, mt->cvtrfpw); 5093 data_bitset (&Regs[0x46], 0x1f, mt->cvtrbpw); 5094 5095 data_lsb_set (&Regs[0x47], mt->cvtrw, 1); 5096 5097 data_lsb_set (&Regs[0x84], mt->cphbp2s, 3); 5098 data_lsb_set (&Regs[0x87], mt->cphbp2e, 3); 5099 5100 data_lsb_set (&Regs[0x8a], mt->clamps, 3); 5101 data_lsb_set (&Regs[0x8d], mt->clampe, 3); 5102 5103 if (dev->chipset->model == RTS8822L_02A) 5104 { 5105 if (mt->clampe == -1) 5106 data_lsb_set (&Regs[0x8d], mt->cphbp2e, 3); 5107 } 5108 5109 Regs[0x97] = get_byte (mt->adcclkp[0]); 5110 Regs[0x98] = get_byte (get_shrd (mt->adcclkp[0], 0x08)); 5111 Regs[0x99] = get_byte (get_shrd (mt->adcclkp[0], 0x10)); 5112 Regs[0x9a] = get_byte (get_shrd (mt->adcclkp[0], 0x18)); 5113 Regs[0x9b] &= 0xf0; 5114 Regs[0x9b] |= ((get_byte (get_shrd (mt->adcclkp[0], 0x20))) & 0x0f); 5115 5116 Regs[0xc1] = get_byte (mt->adcclkp[1]); 5117 Regs[0xc2] = get_byte (get_shrd (mt->adcclkp[1], 0x08)); 5118 Regs[0xc3] = get_byte (get_shrd (mt->adcclkp[1], 0x10)); 5119 Regs[0xc4] = get_byte (get_shrd (mt->adcclkp[1], 0x18)); 5120 Regs[0xc5] &= 0xe0; 5121 Regs[0xc5] |= ((get_byte (get_shrd (mt->adcclkp[1], 0x20))) & 0x0f); 5122 5123 /* bit(4) = bit(0) */ 5124 Regs[0xc5] |= ((mt->adcclkp2e & 1) << 4); 5125 5126 Timing_SetLinearImageSensorClock (&Regs[0x48], &mt->cph[0]); 5127 Timing_SetLinearImageSensorClock (&Regs[0x52], &mt->cph[1]); 5128 Timing_SetLinearImageSensorClock (&Regs[0x5c], &mt->cph[2]); 5129 Timing_SetLinearImageSensorClock (&Regs[0x66], &mt->cph[3]); 5130 Timing_SetLinearImageSensorClock (&Regs[0x70], &mt->cph[4]); 5131 Timing_SetLinearImageSensorClock (&Regs[0x7a], &mt->cph[5]); 5132 } 5133 } 5134} 5135 5136static SANE_Int 5137Motor_GetFromResolution (SANE_Int resolution) 5138{ 5139 SANE_Int ret; 5140 5141 ret = 3; 5142 if (RTS_Debug->usbtype != USB11) 5143 { 5144 if (scan.scantype != ST_NORMAL) 5145 { 5146 /* scantype is ST_NEG or ST_TA */ 5147 if (resolution >= 600) 5148 ret = 0; 5149 } 5150 else if (resolution >= 1200) 5151 ret = 0; 5152 } 5153 else if (resolution >= 600) 5154 ret = 0; 5155 5156 DBG (DBG_FNC, "> Motor_GetFromResolution(resolution=%i): %i\n", resolution, 5157 ret); 5158 5159 return ret; 5160} 5161 5162static SANE_Int 5163SetMultiExposure (struct st_device *dev, SANE_Byte * Regs) 5164{ 5165 SANE_Int iValue, myctpc; 5166 5167 DBG (DBG_FNC, "> SetMultiExposure:\n"); 5168 5169 /* set motor has no curves */ 5170 data_bitset (&Regs[0xdf], 0x10, 0); /*---0----*/ 5171 5172 /* select case systemclock */ 5173 switch (Regs[0x00] & 0x0f) 5174 { 5175 case 0x00: 5176 iValue = 0x00895440; 5177 break; /* 3 x 0x2DC6C0 */ 5178 case 0x08: 5179 case 0x01: 5180 iValue = 0x00b71b00; 5181 break; /* 4 x 0x2DC6C0 */ 5182 case 0x02: 5183 iValue = 0x0112a880; 5184 break; /* 6 x 0x2DC6C0 */ 5185 case 0x0a: 5186 case 0x03: 5187 iValue = 0x016e3600; 5188 break; /* 8 x 0x2DC6C0 */ 5189 case 0x04: 5190 iValue = 0x02255100; 5191 break; /* 12 x 0x2DC6C0 */ 5192 case 0x0c: 5193 iValue = 0x02dc6c00; 5194 break; /* 16 x 0x2DC6C0 */ 5195 case 0x05: 5196 iValue = 0x044aa200; 5197 break; /* 24 x 0x2DC6C0 */ 5198 case 0x0d: 5199 iValue = 0x05b8d800; 5200 break; /* 32 x 0x2DC6C0 */ 5201 5202 case 0x09: 5203 iValue = 0x00f42400; 5204 break; 5205 case 0x0b: 5206 iValue = 0x01e84800; 5207 break; /* = case 9 * 2 */ 5208 default: 5209 iValue = 0x0478f7f8; 5210 break; 5211 } 5212 5213 /* divide by timing.cnpp */ 5214 iValue /= ((Regs[0x96] & 0x3f) + 1); 5215 iValue /= dev->motorcfg->basespeedpps; 5216 5217 /* get line exposure time */ 5218 myctpc = data_lsb_get (&Regs[0x30], 3) + 1; 5219 5220 DBG (DBG_FNC, "CTPC -- SetMultiExposure -- 1 =%i\n", myctpc); 5221 5222 /* if last step of accurve.normalscan table is lower than iValue ... */ 5223 if (data_lsb_get (&Regs[0xe1], 3) < iValue) 5224 { 5225 SANE_Int traget; 5226 SANE_Int step_size = _B0 (Regs[0xe0]) + 1; 5227 5228 /* set exposure time [RED] if zero */ 5229 if (data_lsb_get (&Regs[0x36], 3) == 0) 5230 data_lsb_set (&Regs[0x36], myctpc - 1, 3); 5231 5232 /* set exposure time [GREEN] if zero */ 5233 if (data_lsb_get (&Regs[0x3c], 3) == 0) 5234 data_lsb_set (&Regs[0x3c], myctpc - 1, 3); 5235 5236 /* set exposure time [BLUE] if zero */ 5237 if (data_lsb_get (&Regs[0x42], 3) == 0) 5238 data_lsb_set (&Regs[0x42], myctpc - 1, 3); 5239 5240 iValue = (iValue + 1) * step_size; 5241 5242 /* update line exposure time */ 5243 traget = (((myctpc + iValue - 1) / myctpc) * myctpc); 5244 data_lsb_set (&Regs[0x30], traget - 1, 3); 5245 5246 traget = (traget / step_size) - 1; 5247 data_lsb_set (&Regs[0x00e1], traget, 3); 5248 } 5249 5250 /* 8300 */ 5251 return OK; 5252} 5253 5254static SANE_Int 5255data_lsb_get (SANE_Byte * address, SANE_Int size) 5256{ 5257 SANE_Int ret = 0; 5258 if ((address != NULL) && (size > 0) && (size < 5)) 5259 { 5260 SANE_Int a; 5261 SANE_Byte b; 5262 size--; 5263 for (a = size; a >= 0; a--) 5264 { 5265 b = address[a]; 5266 ret = (ret << 8) + b; 5267 } 5268 } 5269 return ret; 5270} 5271 5272static SANE_Byte 5273data_bitget (SANE_Byte * address, SANE_Int mask) 5274{ 5275 SANE_Int desp = 0; 5276 5277 if (mask & 1); 5278 else if (mask & 2) 5279 desp = 1; 5280 else if (mask & 4) 5281 desp = 2; 5282 else if (mask & 8) 5283 desp = 3; 5284 else if (mask & 16) 5285 desp = 4; 5286 else if (mask & 32) 5287 desp = 5; 5288 else if (mask & 64) 5289 desp = 6; 5290 else if (mask & 128) 5291 desp = 7; 5292 5293 return (*address & mask) >> desp; 5294} 5295 5296static void 5297data_bitset (SANE_Byte * address, SANE_Int mask, SANE_Byte data) 5298{ 5299 /* This function fills mask bits of just a byte with bits given in data */ 5300 if (mask & 1); 5301 else if (mask & 2) 5302 data <<= 1; 5303 else if (mask & 4) 5304 data <<= 2; 5305 else if (mask & 8) 5306 data <<= 3; 5307 else if (mask & 16) 5308 data <<= 4; 5309 else if (mask & 32) 5310 data <<= 5; 5311 else if (mask & 64) 5312 data <<= 6; 5313 else if (mask & 128) 5314 data <<= 7; 5315 5316 *address = (*address & (0xff - mask)) | (data & mask); 5317} 5318 5319static void 5320data_wide_bitset (SANE_Byte * address, SANE_Int mask, SANE_Int data) 5321{ 5322 /* Setting bytes bit per bit 5323 mask is 4 bytes size 5324 Example: 5325 data = 0111010111 5326 mask = 00000000 11111111 11000000 00000000 5327 rst = 00000000 01110101 11000000 00000000 */ 5328 5329 SANE_Int mymask, started = FALSE; 5330 5331 if ((address != NULL) && (mask != 0)) 5332 { 5333 while (mask != 0) 5334 { 5335 mymask = _B0 (mask); 5336 5337 if (started == FALSE) 5338 { 5339 if (mymask != 0) 5340 { 5341 SANE_Int a, myvalue; 5342 5343 for (a = 0; a < 8; a++) 5344 if ((mymask & (1 << a)) != 0) 5345 break; 5346 5347 myvalue = _B0 (data << a); 5348 myvalue >>= a; 5349 data_bitset (address, mymask, myvalue); 5350 data >>= (8 - a); 5351 started = TRUE; 5352 } 5353 } 5354 else 5355 { 5356 data_bitset (address, mymask, _B0 (data)); 5357 data >>= 8; 5358 } 5359 5360 address++; 5361 mask >>= 8; 5362 } 5363 } 5364} 5365 5366 5367static void 5368data_lsb_set (SANE_Byte * address, SANE_Int data, SANE_Int size) 5369{ 5370 if ((address != NULL) && (size > 0) && (size < 5)) 5371 { 5372 SANE_Int a; 5373 for (a = 0; a < size; a++) 5374 { 5375 address[a] = _B0 (data); 5376 data >>= 8; 5377 } 5378 } 5379} 5380 5381static void 5382data_msb_set (SANE_Byte * address, SANE_Int data, SANE_Int size) 5383{ 5384 if ((address != NULL) && (size > 0) && (size < 5)) 5385 { 5386 SANE_Int a; 5387 5388 for (a = size - 1; a >= 0; a--) 5389 { 5390 address[a] = _B0 (data); 5391 data >>= 8; 5392 } 5393 } 5394} 5395 5396static SANE_Int 5397data_swap_endianess (SANE_Int address, SANE_Int size) 5398{ 5399 SANE_Int rst = 0; 5400 5401 if ((size > 0) && (size < 5)) 5402 { 5403 SANE_Int a; 5404 5405 for (a = 0; a < size; a++) 5406 { 5407 rst = (rst << 8) | _B0 (address); 5408 address >>= 8; 5409 } 5410 } 5411 5412 return rst; 5413} 5414 5415static void 5416Lamp_SetGainMode (struct st_device *dev, SANE_Byte * Regs, 5417 SANE_Int resolution, SANE_Byte gainmode) 5418{ 5419 DBG (DBG_FNC, "> Lamp_SetGainMode(*Regs, resolution=%i, gainmode=%i):\n", 5420 resolution, gainmode); 5421 5422 if (dev->chipset->model == RTS8822L_02A) 5423 { 5424 /* hp4370 */ 5425 SANE_Int data1, data2; 5426 5427 data1 = data_lsb_get (&Regs[0x154], 2) & 0xfe7f; 5428 data2 = data_lsb_get (&Regs[0x156], 2); 5429 5430 switch (resolution) 5431 { 5432 case 4800: 5433 data2 |= 0x40; 5434 data1 &= 0xffbf; 5435 break; 5436 case 100: 5437 case 150: 5438 case 200: 5439 case 300: 5440 case 600: 5441 case 1200: 5442 case 2400: 5443 data1 |= 0x40; 5444 data2 &= 0xffbf; 5445 break; 5446 } 5447 5448 data_lsb_set (&Regs[0x154], data1, 2); 5449 data_lsb_set (&Regs[0x156], data2, 2); 5450 } 5451 else 5452 { 5453 /* hp3970 hp4070 ua4900 */ 5454 SANE_Int data; 5455 5456 data = data_lsb_get (&Regs[0x154], 2) & 0xfe7f; 5457 data = (gainmode == FALSE) ? data | 0x0040 : data & 0xffbf; 5458 5459 switch (resolution) 5460 { 5461 case 100: 5462 case 200: 5463 case 300: 5464 case 600: 5465 data |= 0x0100; 5466 break; 5467 case 2400: 5468 data |= 0x0180; 5469 break; 5470 case 1200: 5471 if (dev->sensorcfg->type == CIS_SENSOR) 5472 data |= 0x80; 5473 else if (dev->sensorcfg->type == CCD_SENSOR) 5474 data |= 0x0180; 5475 break; 5476 } 5477 5478 data_lsb_set (&Regs[0x0154], data, 2); 5479 } 5480} 5481 5482static SANE_Int 5483RTS_Scanner_StartScan (struct st_device *dev) 5484{ 5485 SANE_Int rst = ERROR; /* default */ 5486 SANE_Int data; 5487 5488 DBG (DBG_FNC, "+ RTS_Scanner_StartScan():\n"); 5489 5490 v14b4 = 1; /* TEMPORAL */ 5491 data = 0; 5492 Lamp_PWM_DutyCycle_Get (dev, &data); 5493 data = _B0 (data); 5494 5495 DBG (DBG_FNC, "-> Pwm used = %i\n", data); 5496 5497 /* 5498 windows driver saves pwm used, in file usbfile 5499 Section [SCAN_PARAM], field PwmUsed 5500 */ 5501 5502 dev->status->cancel = FALSE; 5503 5504 if (Scan_Start (dev) == OK) 5505 { 5506 SANE_Int transferred; 5507 5508 rst = OK; 5509 5510 if (dev->scanning->imagebuffer != NULL) 5511 { 5512 free (dev->scanning->imagebuffer); 5513 dev->scanning->imagebuffer = NULL; 5514 } 5515 5516 SetLock (dev->usb_handle, NULL, (scan2.depth == 16) ? FALSE : TRUE); 5517 5518 /* Reservamos los buffers necesarios para leer la imagen */ 5519 Reading_CreateBuffers (dev); 5520 5521 if (dev->Resize->type != RSZ_NONE) 5522 Resize_Start (dev, &transferred); /* 6729 */ 5523 5524 RTS_ScanCounter_Inc (dev); 5525 } 5526 5527 DBG (DBG_FNC, "- RTS_Scanner_StartScan: %i\n", rst); 5528 5529 return rst; 5530} 5531 5532static void 5533Triplet_Gray (SANE_Byte * pPointer1, SANE_Byte * pPointer2, 5534 SANE_Byte * buffer, SANE_Int channels_count) 5535{ 5536 /* 5537 pPointer1 = FAB8 5538 pPointer2 = FABC 5539 buffer = FAC0 5540 channels_count = FAC4 5541 */ 5542 5543 SANE_Int value; 5544 SANE_Int channel_size; 5545 5546 DBG (DBG_FNC, 5547 "> Triplet_Gray(*pPointer1, *pPointer2, *buffer, channels_count=%i)\n", 5548 channels_count); 5549 5550 channel_size = (scan2.depth > 8) ? 2 : 1; 5551 channels_count = channels_count / 2; 5552 5553 while (channels_count > 0) 5554 { 5555 value = data_lsb_get (pPointer1, channel_size); 5556 data_lsb_set (buffer, value, channel_size); 5557 5558 value = data_lsb_get (pPointer2, channel_size); 5559 data_lsb_set (buffer + channel_size, value, channel_size); 5560 5561 pPointer1 += 2 * channel_size; 5562 pPointer2 += 2 * channel_size; 5563 buffer += 2 * channel_size; 5564 5565 channels_count--; 5566 } 5567} 5568 5569static void 5570Triplet_Lineart (SANE_Byte * pPointer1, SANE_Byte * pPointer2, 5571 SANE_Byte * buffer, SANE_Int channels_count) 5572{ 5573 /* Composing colour in lineart mode */ 5574 5575 SANE_Int dots_count = 0; 5576 SANE_Int channel; 5577 SANE_Byte mask; 5578 SANE_Byte value; 5579 SANE_Int C; 5580 5581 DBG (DBG_FNC, 5582 "> Triplet_Lineart(*pPointer1, *pPointer2, *buffer, channels_count=%i)\n", 5583 channels_count); 5584 5585 if (channels_count > 0) 5586 { 5587 dots_count = (channels_count + 1) / 2; 5588 while (dots_count > 0) 5589 { 5590 mask = 0x80; 5591 channel = 2; 5592 do 5593 { 5594 value = 0; 5595 for (C = 4; C > 0; C--) 5596 { 5597 value = 5598 (value << 2) + 5599 (((*pPointer2 & mask) << 1) | (*pPointer1 & mask)); 5600 mask = mask >> 1; 5601 } 5602 *buffer = value; 5603 buffer++; 5604 channel--; 5605 } 5606 while (channel > 0); 5607 pPointer2 += 2; 5608 pPointer1 += 2; 5609 dots_count--; 5610 } 5611 } 5612} 5613 5614static SANE_Int 5615Arrange_NonColour (struct st_device *dev, SANE_Byte * buffer, 5616 SANE_Int buffer_size, SANE_Int * transferred) 5617{ 5618 /* 5619 buffer : fadc 5620 buffer_size : fae0 5621 */ 5622 5623 SANE_Int lines_count = 0; /* ebp */ 5624 SANE_Int channels_count = 0; /* fadc pisa buffer */ 5625 SANE_Int rst = ERROR; 5626 struct st_scanning *scn; 5627 5628 DBG (DBG_FNC, 5629 "+ Arrange_NonColour(*buffer, buffer_size=%i, *transferred):\n", 5630 buffer_size); 5631 5632 /* this is just to make code more legible */ 5633 scn = dev->scanning; 5634 5635 if (scn->imagebuffer == NULL) 5636 { 5637 if ((scn->arrange_hres == TRUE) || (scan2.colormode == CM_LINEART)) 5638 { 5639 scn->bfsize = (scn->arrange_sensor_evenodd_dist + 1) * line_size; 5640 scn->imagebuffer = 5641 (SANE_Byte *) malloc (scn->bfsize * sizeof (SANE_Byte)); 5642 if (scn->imagebuffer != NULL) 5643 { 5644 if (Read_Block (dev, scn->bfsize, scn->imagebuffer, transferred) 5645 == OK) 5646 { 5647 scn->channel_size = (scan2.depth == 8) ? 1 : 2; 5648 scn->desp1[CL_RED] = 0; 5649 scn->desp2[CL_RED] = 5650 scn->channel_size + 5651 (scn->arrange_sensor_evenodd_dist * line_size); 5652 scn->pColour2[CL_RED] = 5653 scn->imagebuffer + scn->desp2[CL_RED]; 5654 scn->pColour1[CL_RED] = 5655 scn->imagebuffer + scn->desp1[CL_RED]; 5656 rst = OK; 5657 } 5658 } 5659 } 5660 } 5661 else 5662 rst = OK; 5663 5664 /* b0f4 */ 5665 if (rst == OK) 5666 { 5667 scn->imagepointer = scn->imagebuffer; 5668 lines_count = buffer_size / line_size; 5669 channels_count = line_size / scn->channel_size; 5670 while (lines_count > 0) 5671 { 5672 if (scan2.colormode == CM_LINEART) 5673 Triplet_Lineart (scn->pColour1[CL_RED], scn->pColour2[CL_RED], 5674 buffer, channels_count); 5675 else 5676 Triplet_Gray (scn->pColour1[CL_RED], scn->pColour2[CL_RED], 5677 buffer, channels_count); 5678 5679 buffer += line_size; 5680 scn->arrange_size -= bytesperline; 5681 5682 lines_count--; 5683 if (lines_count == 0) 5684 { 5685 if ((scn->arrange_size | v15bc) == 0) 5686 break; 5687 } 5688 5689 rst = Read_Block (dev, line_size, scn->imagepointer, transferred); 5690 if (rst != OK) 5691 break; 5692 5693 if (scn->arrange_hres == TRUE) 5694 { 5695 scn->desp2[CL_RED] = 5696 (line_size + scn->desp2[CL_RED]) % scn->bfsize; 5697 scn->desp1[CL_RED] = 5698 (line_size + scn->desp1[CL_RED]) % scn->bfsize; 5699 5700 scn->pColour2[CL_RED] = scn->imagebuffer + scn->desp2[CL_RED]; 5701 scn->pColour1[CL_RED] = scn->imagebuffer + scn->desp1[CL_RED]; 5702 } 5703 5704 /* b21d */ 5705 scn->imagepointer += line_size; 5706 if (scn->imagepointer >= (scn->imagebuffer + scn->bfsize)) 5707 scn->imagepointer = scn->imagebuffer; 5708 } 5709 } 5710 5711 /* 2246 */ 5712 5713 DBG (DBG_FNC, "- Arrange_NonColour(*transferred=%i): %i\n", *transferred, 5714 rst); 5715 5716 return rst; 5717} 5718 5719static SANE_Int 5720Resize_Decrease (SANE_Byte * to_buffer, SANE_Int to_resolution, 5721 SANE_Int to_width, SANE_Byte * from_buffer, 5722 SANE_Int from_resolution, SANE_Int from_width, 5723 SANE_Int myresize_mode) 5724{ 5725 /* 5726 to_buffer = FAC8 = 0x236200 5727 to_resolution = FACC = 0x4b 5728 to_width = FAD0 = 0x352 5729 from_buffer = FAD4 = 0x235460 5730 from_resolution = FAD8 = 0x64 5731 from_width = FADC = 0x46d 5732 myresize_mode = FAE0 = 1 5733 */ 5734 5735 SANE_Int rst = ERROR; 5736 SANE_Int channels = 0; /* fac8 */ 5737 SANE_Int depth = 0; /* fae0 */ 5738 SANE_Int color[3] = { 0, 0, 0 }; /* fab8 | fabc | fac0 */ 5739 SANE_Int to_pos = 0; /* fad4 */ 5740 SANE_Int rescont = 0; 5741 SANE_Int from_pos = 0; /* fab4 */ 5742 SANE_Int C; 5743 SANE_Int smres = 0; /* fab0 */ 5744 SANE_Int value; 5745 SANE_Int channel_size; 5746 5747 to_resolution = to_resolution & 0xffff; 5748 from_resolution = from_resolution & 0xffff; 5749 5750 DBG (DBG_FNC, 5751 "+ Resize_Decrease(*to_buffer, to_resolution=%i, to_width=%i, *from_buffer, from_resolution=%i, from_width=%i, myresize_mode=%i):\n", 5752 to_resolution, to_width, from_resolution, from_width, myresize_mode); 5753 5754 if (myresize_mode != RSZ_LINEART) 5755 { 5756 switch (myresize_mode) 5757 { 5758 case RSZ_GRAYL: 5759 channels = 1; 5760 depth = 8; 5761 break; 5762 case RSZ_COLOURL: 5763 channels = 3; 5764 depth = 8; 5765 break; 5766 case RSZ_COLOURH: 5767 channels = 3; 5768 depth = 16; 5769 break; 5770 case RSZ_GRAYH: 5771 channels = 1; 5772 depth = 16; 5773 break; 5774 } 5775 5776 channel_size = (depth > 8) ? 2 : 1; 5777 to_pos = 0; 5778 rescont = 0; 5779 5780 while (to_pos < to_width) 5781 { 5782 from_pos++; 5783 if (from_pos > from_width) 5784 from_buffer -= (((depth + 7) / 8) * channels); 5785 5786 rescont += to_resolution; 5787 if (rescont < from_resolution) 5788 { 5789 /* Adds 3 color channel values */ 5790 for (C = 0; C < channels; C++) 5791 { 5792 color[C] += 5793 data_lsb_get (from_buffer, channel_size) * to_resolution; 5794 from_buffer += channel_size; 5795 } 5796 } 5797 else 5798 { 5799 /* fc3c */ 5800 to_pos++; 5801 smres = to_resolution - (rescont - from_resolution); 5802 for (C = 0; C < channels; C++) 5803 { 5804 value = 5805 ((data_lsb_get (from_buffer, channel_size) * smres) + 5806 color[C]) / from_resolution; 5807 data_lsb_set (to_buffer, value, channel_size); 5808 color[C] = 5809 data_lsb_get (from_buffer, 5810 channel_size) * (rescont - from_resolution); 5811 5812 to_buffer += channel_size; 5813 from_buffer += channel_size; 5814 } 5815 rescont -= from_resolution; 5816 } 5817 } 5818 5819 rst = OK; 5820 } 5821 else 5822 { 5823 /* fd60 */ 5824 SANE_Int bit, pos, desp, rescont2; 5825 5826 *to_buffer = 0; 5827 bit = 0; 5828 pos = 0; 5829 desp = 0; 5830 rescont = 0; 5831 rescont2 = 0; 5832 if (to_width > 0) 5833 { 5834 do 5835 { 5836 if (bit == 8) 5837 { 5838 /* fda6 */ 5839 bit = 0; 5840 to_buffer++; 5841 *to_buffer = 0; 5842 } 5843 5844 rescont += to_resolution; 5845 if (rescont < from_resolution) 5846 { 5847 if ((*from_buffer & (0x80 >> desp)) != 0) 5848 rescont2 += to_resolution; 5849 } 5850 else 5851 { 5852 /*fdd5 */ 5853 pos++; 5854 rescont -= from_resolution; 5855 if ((*from_buffer & (0x80 >> desp)) != 0) 5856 /*fdee */ 5857 rescont2 += (to_resolution - rescont); 5858 if (rescont2 > (to_resolution / 2)) 5859 /* fe00 */ 5860 *to_buffer = _B0 (*to_buffer | (0x80 >> bit)); 5861 rescont2 = 5862 ((*from_buffer & (0x80 >> desp)) != 0) ? rescont : 0; 5863 bit++; 5864 } 5865 5866 /* fe2f */ 5867 desp++; 5868 if (desp == 8) 5869 { 5870 desp = 0; 5871 from_buffer++; 5872 } 5873 } 5874 while (pos < to_width); 5875 } 5876 else 5877 rst = OK; 5878 } 5879 5880 DBG (DBG_FNC, "- Resize_Decrease: %i\n", rst); 5881 5882 return rst; 5883} 5884 5885static SANE_Int 5886Resize_Increase (SANE_Byte * to_buffer, SANE_Int to_resolution, 5887 SANE_Int to_width, SANE_Byte * from_buffer, 5888 SANE_Int from_resolution, SANE_Int from_width, 5889 SANE_Int myresize_mode) 5890{ 5891 /* 5892 5893 to_buffer = FAC8 = 0x2353f0 5894 to_resolution = FACC = 0x4b 5895 to_width = FAD0 = 0x352 5896 from_buffer = FAD4 = 0x234650 5897 from_resolution = FAD8 = 0x64 5898 from_width = FADC = 0x46d 5899 myresize_mode = FAE0 = 1 5900 */ 5901 5902 SANE_Int rst = ERROR; 5903 SANE_Int desp; /* fac0 */ 5904 SANE_Byte *myp2; /* faac */ 5905 SANE_Int mywidth; /* fab4 fab8 */ 5906 SANE_Int mychannels; /* fabc */ 5907 SANE_Int channels = 0; /* faa4 */ 5908 SANE_Int depth = 0; /* faa8 */ 5909 SANE_Int pos = 0; /* fae0 */ 5910 SANE_Int rescount; 5911 SANE_Int val6 = 0; 5912 SANE_Int val7 = 0; 5913 SANE_Int value; 5914 /**/ 5915 DBG (DBG_FNC, 5916 "+ Resize_Increase(*to_buffer, to_resolution=%i, to_width=%i, *from_buffer, from_resolution=%i, from_width=%i, myresize_mode=%i):\n", 5917 to_resolution, to_width, from_resolution, from_width, myresize_mode); 5918 5919 if (myresize_mode != RSZ_LINEART) 5920 { 5921 switch (myresize_mode) 5922 { 5923 case RSZ_GRAYL: 5924 channels = 1; 5925 depth = 8; 5926 break; 5927 case RSZ_COLOURL: 5928 channels = 3; 5929 depth = 8; 5930 break; 5931 case RSZ_COLOURH: 5932 channels = 3; 5933 depth = 16; 5934 break; 5935 case RSZ_GRAYH: 5936 channels = 1; 5937 depth = 16; 5938 break; 5939 } 5940 5941 if (channels > 0) 5942 { 5943 SANE_Byte channel_size; 5944 SANE_Byte *p_dst; /* fac8 */ 5945 SANE_Byte *p_src; /* fad4 */ 5946 5947 desp = to_buffer - from_buffer; 5948 myp2 = from_buffer; 5949 channel_size = (depth == 8) ? 1 : 2; 5950 5951 for (mychannels = 0; mychannels < channels; mychannels++) 5952 { 5953 pos = 0; 5954 rescount = (from_resolution / 2) + to_resolution; 5955 5956 p_src = myp2; 5957 p_dst = myp2 + desp; 5958 5959 /* f938 */ 5960 val7 = data_lsb_get (p_src, channel_size); 5961 5962 if (to_width > 0) 5963 { 5964 for (mywidth = 0; mywidth < to_width; mywidth++) 5965 { 5966 if (rescount >= to_resolution) 5967 { 5968 rescount -= to_resolution; 5969 val6 = val7; 5970 pos++; 5971 if (pos < from_width) 5972 { 5973 p_src += (channels * channel_size); 5974 val7 = data_lsb_get (p_src, channel_size); 5975 } 5976 } 5977 5978 /*f9a5 */ 5979 data_lsb_set (p_dst, 5980 ((((to_resolution - rescount) * val6) + 5981 (val7 * rescount)) / to_resolution), 5982 channel_size); 5983 rescount += from_resolution; 5984 p_dst += (channels * channel_size); 5985 } 5986 } 5987 5988 myp2 += channel_size; 5989 } 5990 5991 rst = OK; 5992 } 5993 else 5994 rst = OK; 5995 } 5996 else 5997 { 5998 /* RSZ_LINEART mode */ 5999 /* fa02 */ 6000 /* 6001 to_buffer = FAC8 = 0x2353f0 6002 to_resolution = FACC = 0x4b 6003 to_width = FAD0 = 0x352 6004 from_buffer = FAD4 = 0x234650 6005 from_resolution = FAD8 = 0x64 6006 from_width = FADC = 0x46d 6007 myresize_mode = FAE0 = 1 6008 */ 6009 SANE_Int myres2; /* fac8 */ 6010 SANE_Int sres; 6011 SANE_Int lfae0; 6012 SANE_Int lfad8; 6013 SANE_Int myres; 6014 SANE_Int cont = 1; 6015 SANE_Int someval; 6016 SANE_Int bit; /*lfaa8 */ 6017 6018 myres2 = from_resolution; 6019 sres = (myres2 / 2) + to_resolution; 6020 value = _B0 (*from_buffer); 6021 bit = 0; 6022 lfae0 = 0; 6023 lfad8 = value >> 7; 6024 someval = lfad8; 6025 *to_buffer = 0; 6026 6027 if (to_width > 0) 6028 { 6029 myres = to_resolution; 6030 to_resolution = myres / 2; 6031 do 6032 { 6033 if (sres >= myres) 6034 { 6035 sres -= myres; 6036 lfae0++; 6037 cont++; 6038 lfad8 = someval; 6039 if (lfae0 < from_width) 6040 { 6041 if (cont == 8) 6042 { 6043 cont = 0; 6044 from_buffer++; 6045 } 6046 bit = (((0x80 >> cont) & *from_buffer) != 0) ? 1 : 0; 6047 } 6048 } 6049 /*faa6 */ 6050 if ((((myres - sres) * lfad8) + (bit * sres)) > to_resolution) 6051 *to_buffer |= (0x80 >> bit); 6052 6053 bit++; 6054 if (bit == 8) 6055 { 6056 bit = 0; 6057 to_buffer++; 6058 *to_buffer = 0; 6059 } 6060 to_width--; 6061 sres += myres2; 6062 } 6063 while (to_width > 0); 6064 rst = OK; 6065 } 6066 } 6067 6068 DBG (DBG_FNC, "- Resize_Increase: %i\n", rst); 6069 6070 return rst; 6071} 6072 6073static SANE_Int 6074Resize_Start (struct st_device *dev, SANE_Int * transferred) 6075{ 6076 SANE_Int rst = ERROR; 6077 struct st_resize *rz = dev->Resize; 6078 6079 DBG (DBG_FNC, "+ Resize_Start(*transferred):\n"); 6080 6081 if (Resize_CreateBuffers 6082 (dev, line_size, rz->bytesperline, rz->bytesperline) == ERROR) 6083 return ERROR; 6084 6085 if (arrangeline2 == FIX_BY_SOFT) 6086 { 6087 /* fee0 */ 6088 if (scan2.colormode == CM_COLOR) 6089 rst = Arrange_Colour (dev, rz->v3624, line_size, transferred); 6090 else 6091 rst = Arrange_NonColour (dev, rz->v3624, line_size, transferred); 6092 } 6093 else 6094 rst = Read_Block (dev, line_size, rz->v3624, transferred); /* ff03 */ 6095 6096 /* Redimensionado */ 6097 switch (rz->type) 6098 { 6099 case RSZ_DECREASE: 6100 /* ff1b */ 6101 Resize_Decrease (rz->v3628, rz->resolution_x, rz->towidth, rz->v3624, 6102 scan2.resolution_x, rz->fromwidth, rz->mode); 6103 break; 6104 case RSZ_INCREASE: 6105 /* ff69 */ 6106 rz->rescount = 0; 6107 Resize_Increase (rz->v3628, rz->resolution_x, rz->towidth, rz->v3624, 6108 scan2.resolution_x, rz->fromwidth, rz->mode); 6109 if (arrangeline2 == FIX_BY_SOFT) 6110 { 6111 /* ffb1 */ 6112 if (scan2.colormode == CM_COLOR) 6113 rst = Arrange_Colour (dev, rz->v3624, line_size, transferred); 6114 else 6115 rst = Arrange_NonColour (dev, rz->v3624, line_size, transferred); 6116 } 6117 else 6118 rst = Read_Block (dev, line_size, rz->v3624, transferred); /* ffe0 */ 6119 6120 /* fff2 */ 6121 Resize_Increase (rz->v362c, rz->resolution_x, rz->towidth, rz->v3624, 6122 scan2.resolution_x, rz->fromwidth, rz->mode); 6123 break; 6124 } 6125 6126 /* 002a */ 6127 6128 DBG (DBG_FNC, "- Resize_Start(*transferred=%i): %i\n", *transferred, rst); 6129 6130 return rst; 6131} 6132 6133static SANE_Int 6134Resize_CreateBuffers (struct st_device *dev, SANE_Int size1, SANE_Int size2, 6135 SANE_Int size3) 6136{ 6137 SANE_Int rst = ERROR; 6138 struct st_resize *rz = dev->Resize; 6139 6140 rz->v3624 = (SANE_Byte *) malloc ((size1 + 0x40) * sizeof (SANE_Byte)); 6141 rz->v3628 = (SANE_Byte *) malloc ((size2 + 0x40) * sizeof (SANE_Byte)); 6142 rz->v362c = (SANE_Byte *) malloc ((size3 + 0x40) * sizeof (SANE_Byte)); 6143 6144 if ((rz->v3624 == NULL) || (rz->v3628 == NULL) || (rz->v362c == NULL)) 6145 Resize_DestroyBuffers (dev); 6146 else 6147 rst = OK; 6148 6149 DBG (DBG_FNC, "> Resize_CreateBuffers(size1=%i, size2=%i, size3=%i): %i\n", 6150 size1, size2, size3, rst); 6151 6152 return rst; 6153} 6154 6155static SANE_Int 6156Resize_DestroyBuffers (struct st_device *dev) 6157{ 6158 struct st_resize *rz = dev->Resize; 6159 6160 if (rz->v3624 != NULL) 6161 free (rz->v3624); 6162 6163 if (rz->v3628 != NULL) 6164 free (rz->v3628); 6165 6166 if (rz->v362c != NULL) 6167 free (rz->v362c); 6168 6169 rz->v3624 = NULL; 6170 rz->v3628 = NULL; 6171 rz->v362c = NULL; 6172 6173 return OK; 6174} 6175 6176static SANE_Int 6177Reading_DestroyBuffers (struct st_device *dev) 6178{ 6179 DBG (DBG_FNC, "> Reading_DestroyBuffers():\n"); 6180 6181 if (dev->Reading->DMABuffer != NULL) 6182 free (dev->Reading->DMABuffer); 6183 6184 if (dev->scanning->imagebuffer != NULL) 6185 { 6186 free (dev->scanning->imagebuffer); 6187 dev->scanning->imagebuffer = NULL; 6188 } 6189 6190 memset (dev->Reading, 0, sizeof (struct st_readimage)); 6191 6192 return OK; 6193} 6194 6195static SANE_Int 6196Gamma_SendTables (struct st_device *dev, SANE_Byte * Regs, 6197 SANE_Byte * gammatable, SANE_Int size) 6198{ 6199 SANE_Int rst = ERROR; 6200 6201 DBG (DBG_FNC, "+ Gamma_SendTables(*Regs, *gammatable, size=%i):\n", size); 6202 6203 if ((gammatable != NULL) && (size > 0)) 6204 { 6205 SANE_Int transferred; 6206 SANE_Int first_table; 6207 SANE_Int cont = 0; 6208 SANE_Int retry = TRUE; 6209 SANE_Byte *mybuffer; 6210 6211 /* lock */ 6212 SetLock (dev->usb_handle, Regs, TRUE); 6213 6214 first_table = (data_lsb_get (&Regs[0x1b4], 2) & 0x3fff) >> 4; 6215 6216 mybuffer = (SANE_Byte *) malloc (sizeof (SANE_Byte) * size); 6217 if (mybuffer != NULL) 6218 { 6219 /* Try to send buffer during 10 seconds */ 6220 long tick = GetTickCount () + 10000; 6221 while ((retry == TRUE) && (tick > GetTickCount ())) 6222 { 6223 retry = FALSE; 6224 6225 /* Operation type 0x14 */ 6226 if (IWrite_Word (dev->usb_handle, 0x0000, 0x0014, 0x0800) == OK) 6227 { 6228 /* Send size to write */ 6229 if (RTS_DMA_Enable_Write (dev, 0x0000, size, first_table) == 6230 OK) 6231 { 6232 /* Send data */ 6233 if (Bulk_Operation 6234 (dev, BLK_WRITE, size, gammatable, 6235 &transferred) == OK) 6236 { 6237 /* Send size to read */ 6238 if (RTS_DMA_Enable_Read 6239 (dev, 0x0000, size, first_table) == OK) 6240 { 6241 /* Retrieve data */ 6242 if (Bulk_Operation 6243 (dev, BLK_READ, size, mybuffer, 6244 &transferred) == OK) 6245 { 6246 /* Check data */ 6247 while ((cont < size) && (retry == FALSE)) 6248 { 6249 if (mybuffer[cont] != gammatable[cont]) 6250 retry = TRUE; 6251 cont++; 6252 } 6253 6254 if (retry == FALSE) 6255 rst = OK; 6256 } 6257 } 6258 } 6259 } 6260 } 6261 } 6262 6263 free (mybuffer); 6264 } 6265 6266 /* unlock */ 6267 SetLock (dev->usb_handle, Regs, FALSE); 6268 } 6269 6270 DBG (DBG_FNC, "- Gamma_SendTables: %i\n", rst); 6271 6272 return rst; 6273} 6274 6275static SANE_Int 6276Gamma_GetTables (struct st_device *dev, SANE_Byte * Gamma_buffer) 6277{ 6278 SANE_Int rst = ERROR; 6279 6280 DBG (DBG_FNC, "+ Gamma_GetTables(SANE_Byte *Gamma_buffer):\n"); 6281 6282 if (Gamma_buffer == NULL) 6283 return ERROR; 6284 6285 /* Operation type 0x14 */ 6286 if (IWrite_Word (dev->usb_handle, 0x0000, 0x0014, 0x0800) == 0x00) 6287 { 6288 SANE_Int size = 768; 6289 6290 if (RTS_DMA_Enable_Read (dev, 0x0000, size, 0) == OK) 6291 { 6292 SANE_Int transferred = 0; 6293 usleep (1000 * 500); 6294 6295 /* Read buffer */ 6296 rst = 6297 Bulk_Operation (dev, BLK_READ, size, Gamma_buffer, &transferred); 6298 } 6299 } 6300 6301 DBG (DBG_FNC, "- Gamma_GetTables: %i\n", rst); 6302 6303 return rst; 6304} 6305 6306static void 6307Gamma_FreeTables () 6308{ 6309 SANE_Int c; 6310 6311 DBG (DBG_FNC, "> Gamma_FreeTables()\n"); 6312 6313 for (c = 0; c < 3; c++) 6314 { 6315 if (hp_gamma->table[c] != NULL) 6316 { 6317 free (hp_gamma->table[c]); 6318 hp_gamma->table[c] = NULL; 6319 } 6320 } 6321 use_gamma_tables = FALSE; 6322} 6323 6324static void 6325RTS_Scanner_StopScan (struct st_device *dev, SANE_Int wait) 6326{ 6327 SANE_Byte data; 6328 6329 DBG (DBG_FNC, "+ RTS_Scanner_StopScan():\n"); 6330 6331 data = 0; 6332 6333 Reading_DestroyBuffers (dev); 6334 Resize_DestroyBuffers (dev); 6335 6336 RTS_DMA_Reset (dev); 6337 6338 data_bitset (&dev->init_regs[0x60b], 0x10, 0); 6339 data_bitset (&dev->init_regs[0x60a], 0x40, 0); 6340 6341 if (Write_Buffer (dev->usb_handle, 0xee0a, &dev->init_regs[0x60a], 2) == OK) 6342 Motor_Change (dev, dev->init_regs, 3); 6343 6344 usleep (1000 * 200); 6345 6346 if (wait == FALSE) 6347 { 6348 Read_Byte (dev->usb_handle, 0xe801, &data); 6349 if ((data & 0x02) == 0) 6350 { 6351 if (Head_IsAtHome (dev, dev->init_regs) == FALSE) 6352 { 6353 /* clear execution bit */ 6354 data_bitset (&dev->init_regs[0x00], 0x80, 0); 6355 6356 Write_Byte (dev->usb_handle, 0x00, dev->init_regs[0x00]); 6357 Head_ParkHome (dev, TRUE, dev->motorcfg->parkhomemotormove); 6358 } 6359 } 6360 } 6361 else 6362 { 6363 /*66a1 */ 6364 /* clear execution bit */ 6365 data_bitset (&dev->init_regs[0x00], 0x80, 0); 6366 6367 Write_Byte (dev->usb_handle, 0x00, dev->init_regs[0x00]); 6368 if (Head_IsAtHome (dev, dev->init_regs) == FALSE) 6369 Head_ParkHome (dev, TRUE, dev->motorcfg->parkhomemotormove); 6370 } 6371 6372 /*66e0 */ 6373 RTS_Enable_CCD (dev, dev->init_regs, 0); 6374 6375 Lamp_Status_Timer_Set (dev, 13); 6376 6377 DBG (DBG_FNC, "- RTS_Scanner_StopScan()\n"); 6378} 6379 6380static SANE_Int 6381Reading_CreateBuffers (struct st_device *dev) 6382{ 6383 SANE_Byte data; 6384 SANE_Int mybytesperline; 6385 SANE_Int mybuffersize, a, b; 6386 6387 DBG (DBG_FNC, "+ Reading_CreateBuffers():\n"); 6388 6389 data = 0; 6390 6391 /* Gets BinarythresholdH */ 6392 if (Read_Byte (dev->usb_handle, 0xe9a1, &data) == OK) 6393 binarythresholdh = data; 6394 6395 mybytesperline = 6396 (scan2.depth == 12) ? (bytesperline * 3) / 4 : bytesperline; 6397 6398 dev->Reading->Max_Size = 0xfc00; 6399 dev->Reading->DMAAmount = 0; 6400 6401 a = (RTS_Debug->dmabuffersize / 63); 6402 b = (((RTS_Debug->dmabuffersize - a) / 2) + a) >> 0x0f; 6403 mybuffersize = ((b << 6) - b) << 10; 6404 if (mybuffersize < 0x1f800) 6405 mybuffersize = 0x1f800; 6406 6407 dev->Reading->DMABufferSize = mybuffersize; /*3FFC00 4193280 */ 6408 6409 do 6410 { 6411 dev->Reading->DMABuffer = 6412 (SANE_Byte *) malloc (dev->Reading->DMABufferSize * 6413 sizeof (SANE_Byte)); 6414 if (dev->Reading->DMABuffer != NULL) 6415 break; 6416 dev->Reading->DMABufferSize -= dev->Reading->Max_Size; 6417 } 6418 while (dev->Reading->DMABufferSize >= dev->Reading->Max_Size); 6419 6420 /* 6003 */ 6421 dev->Reading->Starting = TRUE; 6422 6423 dev->Reading->Size4Lines = (mybytesperline > dev->Reading->Max_Size) ? 6424 mybytesperline : (dev->Reading->Max_Size / mybytesperline) * 6425 mybytesperline; 6426 6427 dev->Reading->ImageSize = imagesize; 6428 read_v15b4 = v15b4; 6429 6430 DBG (DBG_FNC, "- Reading_CreateBuffers():\n"); 6431 6432 return OK; 6433} 6434 6435static SANE_Int 6436RTS_ScanCounter_Inc (struct st_device *dev) 6437{ 6438 /* Keep a count of the number of scans done by this scanner */ 6439 6440 SANE_Int idata; 6441 6442 DBG (DBG_FNC, "+ RTS_ScanCounter_Inc():\n"); 6443 6444 /* check if chipset supports accessing eeprom */ 6445 if ((dev->chipset->capabilities & CAP_EEPROM) != 0) 6446 { 6447 SANE_Byte cdata = 0; 6448 SANE_Byte somebuffer[26]; 6449 6450 switch (dev->chipset->model) 6451 { 6452 case RTS8822L_02A: 6453 case RTS8822BL_03A: 6454 /* value is 4 bytes size starting from address 0x21 in msb format */ 6455 if (RTS_EEPROM_ReadInteger (dev->usb_handle, 0x21, &idata) == OK) 6456 { 6457 idata = data_swap_endianess (idata, 4) + 1; 6458 idata = data_swap_endianess (idata, 4); 6459 RTS_EEPROM_WriteInteger (dev->usb_handle, 0x21, idata); 6460 } 6461 break; 6462 default: 6463 /* value is 4 bytes size starting from address 0x21 in lsb format */ 6464 memset (&somebuffer, 0, sizeof (somebuffer)); 6465 somebuffer[4] = 0x0c; 6466 6467 RTS_EEPROM_ReadInteger (dev->usb_handle, 0x21, &idata); 6468 data_lsb_set (&somebuffer[0], idata + 1, 4); 6469 6470 RTS_EEPROM_ReadByte (dev->usb_handle, 0x003a, &cdata); 6471 somebuffer[25] = cdata; 6472 RTS_EEPROM_WriteBuffer (dev->usb_handle, 0x21, somebuffer, 0x1a); 6473 break; 6474 } 6475 } 6476 6477 DBG (DBG_FNC, "- RTS_ScanCounter_Inc()\n"); 6478 6479 return OK; 6480} 6481 6482static SANE_Int 6483RTS_ScanCounter_Get (struct st_device *dev) 6484{ 6485 /* Returns the number of scans done by this scanner */ 6486 6487 SANE_Int idata = 0; 6488 6489 DBG (DBG_FNC, "+ RTS_ScanCounter_Get():\n"); 6490 6491 /* check if chipset supports accessing eeprom */ 6492 if ((dev->chipset->capabilities & CAP_EEPROM) != 0) 6493 { 6494 RTS_EEPROM_ReadInteger (dev->usb_handle, 0x21, &idata); 6495 6496 switch (dev->chipset->model) 6497 { 6498 case RTS8822L_02A: 6499 case RTS8822BL_03A: 6500 /* value is 4 bytes size starting from address 0x21 in msb format */ 6501 idata = data_swap_endianess (idata, 4); 6502 break; 6503 default: /* RTS8822L_01H */ 6504 /* value is 4 bytes size starting from address 0x21 in lsb format */ 6505 idata &= 0xffffffff; 6506 break; 6507 } 6508 } 6509 6510 DBG (DBG_FNC, "- RTS_ScanCounter_Get(): %i\n", idata); 6511 6512 return idata; 6513} 6514 6515static SANE_Int 6516Read_Image (struct st_device *dev, SANE_Int buffer_size, SANE_Byte * buffer, 6517 SANE_Int * transferred) 6518{ 6519 SANE_Int rst; 6520 SANE_Byte mycolormode; 6521 6522 DBG (DBG_FNC, "+ Read_Image(buffer_size=%i, *buffer, *transferred):\n", 6523 buffer_size); 6524 6525 *transferred = 0; 6526 mycolormode = scan2.colormode; 6527 rst = ERROR; 6528 if ((scan2.colormode != CM_COLOR) && (scan2.channel == 3)) 6529 mycolormode = 3; 6530 6531 if (dev->Resize->type == RSZ_NONE) 6532 { 6533 if (arrangeline == FIX_BY_SOFT) 6534 { 6535 switch (mycolormode) 6536 { 6537 case CM_COLOR: 6538 rst = Arrange_Colour (dev, buffer, buffer_size, transferred); 6539 break; 6540 case 3: 6541 rst = Arrange_Compose (dev, buffer, buffer_size, transferred); 6542 break; 6543 default: 6544 rst = Arrange_NonColour (dev, buffer, buffer_size, transferred); 6545 break; 6546 } 6547 } 6548 else 6549 rst = Read_Block (dev, buffer_size, buffer, transferred); /*00fe */ 6550 } 6551 else 6552 rst = Read_ResizeBlock (dev, buffer, buffer_size, transferred); /*010d */ 6553 6554 DBG (DBG_FNC, "- Read_Image(*transferred=%i): %i\n", *transferred, rst); 6555 6556 return rst; 6557} 6558 6559static SANE_Int 6560Arrange_Compose (struct st_device *dev, SANE_Byte * buffer, 6561 SANE_Int buffer_size, SANE_Int * transferred) 6562{ 6563 /* 6564 fnb250 6565 6566 0600FA7C 05E10048 buffer 6567 0600FA80 0000F906 buffer_size 6568 */ 6569 SANE_Byte *mybuffer = buffer; /* fa7c */ 6570 SANE_Int mydistance; /*ebp */ 6571 SANE_Int mydots; /*fa74 */ 6572 SANE_Int channel_size; 6573 SANE_Int c; 6574 struct st_scanning *scn; 6575 6576 /*mywidth = fa70 */ 6577 6578 DBG (DBG_FNC, "+ Arrange_Compose(*buffer, buffer_size=%i, *transferred):\n", 6579 buffer_size); 6580 6581 channel_size = (scan2.depth == 8) ? 1 : 2; 6582 6583 /* this is just to make code more legible */ 6584 scn = dev->scanning; 6585 6586 if (scn->imagebuffer == NULL) 6587 { 6588 if (dev->sensorcfg->type == CCD_SENSOR) 6589 mydistance = 6590 (dev->sensorcfg->line_distance * scan2.resolution_y) / 6591 dev->sensorcfg->resolution; 6592 else 6593 mydistance = 0; 6594 6595 if (mydistance != 0) 6596 { 6597 scn->bfsize = 6598 (scn->arrange_hres == 6599 TRUE) ? scn->arrange_sensor_evenodd_dist : 0; 6600 scn->bfsize = line_size * (scn->bfsize + (mydistance * 2) + 1); 6601 } 6602 else 6603 scn->bfsize = line_size * 2; 6604 6605 /*b2f0 */ 6606 scn->imagebuffer = 6607 (SANE_Byte *) malloc (scn->bfsize * sizeof (SANE_Byte)); 6608 if (scn->imagebuffer == NULL) 6609 return ERROR; 6610 6611 scn->imagepointer = scn->imagebuffer; 6612 if (Read_Block (dev, scn->bfsize, scn->imagebuffer, transferred) == 6613 ERROR) 6614 return ERROR; 6615 6616 /* Calculate channel displacements */ 6617 scn->arrange_orderchannel = FALSE; 6618 for (c = CL_RED; c <= CL_BLUE; c++) 6619 { 6620 if (mydistance == 0) 6621 { 6622 /*b34e */ 6623 if (scn->arrange_hres == FALSE) 6624 { 6625 if ((((dev->sensorcfg->line_distance * scan2.resolution_y) * 6626 2) / dev->sensorcfg->resolution) == 1) 6627 scn->arrange_orderchannel = TRUE; 6628 6629 if (scn->arrange_orderchannel == TRUE) 6630 scn->desp[c] = 6631 ((dev->sensorcfg->rgb_order[c] / 2) * line_size) + 6632 (channel_size * c); 6633 else 6634 scn->desp[c] = channel_size * c; 6635 } 6636 } 6637 else 6638 { 6639 /*b3e3 */ 6640 scn->desp[c] = 6641 (dev->sensorcfg->rgb_order[c] * (mydistance * line_size)) + 6642 (channel_size * c); 6643 6644 if (scn->arrange_hres == TRUE) 6645 { 6646 /*b43b */ 6647 scn->desp1[c] = scn->desp[c]; 6648 scn->desp2[c] = 6649 ((channel_size * 3) + scn->desp1[c]) + 6650 (scn->arrange_sensor_evenodd_dist * line_size); 6651 }; 6652 } 6653 } 6654 6655 for (c = CL_RED; c <= CL_BLUE; c++) 6656 { 6657 if (scn->arrange_hres == TRUE) 6658 { 6659 scn->pColour2[c] = scn->imagebuffer + scn->desp2[c]; 6660 scn->pColour1[c] = scn->imagebuffer + scn->desp1[c]; 6661 } 6662 else 6663 scn->pColour[c] = scn->imagebuffer + scn->desp[c]; 6664 } 6665 } 6666 6667 /*b545 */ 6668 buffer_size /= line_size; 6669 mydots = line_size / (channel_size * 3); 6670 6671 while (buffer_size > 0) 6672 { 6673 if (scn->arrange_orderchannel == FALSE) 6674 { 6675 /*b5aa */ 6676 if (scn->arrange_hres == TRUE) 6677 Triplet_Compose_HRes (scn->pColour1[CL_RED], 6678 scn->pColour1[CL_GREEN], 6679 scn->pColour1[CL_BLUE], 6680 scn->pColour2[CL_RED], 6681 scn->pColour2[CL_GREEN], 6682 scn->pColour2[CL_BLUE], mybuffer, mydots); 6683 else 6684 Triplet_Compose_LRes (scn->pColour[CL_RED], 6685 scn->pColour[CL_GREEN], 6686 scn->pColour[CL_BLUE], mybuffer, mydots); 6687 } 6688 else 6689 Triplet_Compose_Order (dev, scn->pColour[CL_RED], 6690 scn->pColour[CL_GREEN], scn->pColour[CL_BLUE], 6691 mybuffer, mydots); 6692 6693 /*b5f8 */ 6694 mybuffer += line_size; 6695 scn->arrange_size -= bytesperline; 6696 if (scn->arrange_size < 0) 6697 v15bc--; 6698 6699 buffer_size--; 6700 if (buffer_size == 0) 6701 { 6702 if ((scn->arrange_size | v15bc) == 0) 6703 return OK; 6704 } 6705 6706 /*b63f */ 6707 if (Read_Block (dev, line_size, scn->imagepointer, transferred) == 6708 ERROR) 6709 return ERROR; 6710 6711 for (c = CL_RED; c <= CL_BLUE; c++) 6712 { 6713 if (scn->arrange_hres == TRUE) 6714 { 6715 /*b663 */ 6716 scn->desp2[c] = (scn->desp2[c] + line_size) % scn->bfsize; 6717 scn->desp1[c] = (scn->desp1[c] + line_size) % scn->bfsize; 6718 6719 scn->pColour2[c] = scn->imagebuffer + scn->desp2[c]; 6720 scn->pColour1[c] = scn->imagebuffer + scn->desp1[c]; 6721 } 6722 else 6723 { 6724 /*b74a */ 6725 scn->desp[c] = (scn->desp[c] + line_size) % scn->bfsize; 6726 scn->pColour[c] = scn->imagebuffer + scn->desp[c]; 6727 } 6728 } 6729 6730 /*b7be */ 6731 scn->imagepointer += line_size; 6732 if (scn->imagepointer >= (scn->imagebuffer + scn->bfsize)) 6733 scn->imagepointer = scn->imagebuffer; 6734 } 6735 6736 return OK; 6737} 6738 6739static void 6740Triplet_Compose_HRes (SANE_Byte * pRed1, SANE_Byte * pGreen1, 6741 SANE_Byte * pBlue1, SANE_Byte * pRed2, 6742 SANE_Byte * pGreen2, SANE_Byte * pBlue2, 6743 SANE_Byte * buffer, SANE_Int Width) 6744{ 6745 SANE_Int Value; 6746 SANE_Int Channel_size; 6747 SANE_Int max_value; 6748 6749 DBG (DBG_FNC, 6750 "> Triplet_Compose_HRes(*pRed1, *pGreen1, *pBlue1, *pRed2 *pGreen2, *pBlue2, *buffer, Width=%i):\n", 6751 Width); 6752 6753 Width /= 2; 6754 Channel_size = (scan2.depth > 8) ? 2 : 1; 6755 max_value = (1 << scan2.depth) - 1; 6756 6757 while (Width > 0) 6758 { 6759 Value = 6760 data_lsb_get (pRed1, Channel_size) + data_lsb_get (pGreen1, 6761 Channel_size) + 6762 data_lsb_get (pBlue1, Channel_size); 6763 6764 Value = min (Value, max_value); 6765 6766 if (v1600 != NULL) 6767 { 6768 if (scan2.depth > 8) 6769 Value = *(v1600 + (Value >> 8)) | _B0 (Value); 6770 else 6771 Value = *(v1600 + Value); 6772 } 6773 6774 data_lsb_set (buffer, Value, Channel_size); 6775 buffer += Channel_size; 6776 6777 Value = 6778 data_lsb_get (pRed2, Channel_size) + data_lsb_get (pGreen2, 6779 Channel_size) + 6780 data_lsb_get (pBlue2, Channel_size); 6781 6782 Value = min (Value, max_value); 6783 6784 if (v1600 != NULL) 6785 { 6786 if (scan2.depth > 8) 6787 Value = *(v1600 + (Value >> 8)) | _B0 (Value); 6788 else 6789 Value = *(v1600 + Value); 6790 } 6791 6792 data_lsb_set (buffer, Value, Channel_size); 6793 buffer += Channel_size; 6794 6795 pRed1 += 6 * Channel_size; 6796 pGreen1 += 6 * Channel_size; 6797 pBlue1 += 6 * Channel_size; 6798 6799 pRed2 += 6 * Channel_size; 6800 pGreen2 += 6 * Channel_size; 6801 pBlue2 += 6 * Channel_size; 6802 6803 Width--; 6804 } 6805} 6806 6807static void 6808Triplet_Compose_Order (struct st_device *dev, SANE_Byte * pRed, 6809 SANE_Byte * pGreen, SANE_Byte * pBlue, 6810 SANE_Byte * buffer, SANE_Int dots) 6811{ 6812 SANE_Int Value; 6813 6814 DBG (DBG_FNC, 6815 "> Triplet_Compose_Order(*pRed, *pGreen, *pBlue, *buffer, dots=%i):\n", 6816 dots); 6817 6818 if (scan2.depth > 8) 6819 { 6820 /* c0fe */ 6821 dots = dots / 2; 6822 while (dots > 0) 6823 { 6824 Value = 6825 min (data_lsb_get (pRed, 2) + data_lsb_get (pGreen, 2) + 6826 data_lsb_get (pBlue, 2), 0xffff); 6827 6828 if (v1600 != NULL) 6829 Value = (*(v1600 + (Value >> 8)) << 8) | _B0 (Value); 6830 6831 data_lsb_set (buffer, Value, 2); 6832 6833 buffer += 2; 6834 pRed += 6; 6835 pGreen += 6; 6836 pBlue += 6; 6837 dots--; 6838 } 6839 } 6840 else 6841 { 6842 SANE_Byte *myp1, *myp2, *myp3; 6843 6844 if (dev->sensorcfg->rgb_order[CL_RED] == 1) 6845 { 6846 myp1 = pRed; 6847 myp2 = pGreen; 6848 myp3 = pBlue; 6849 } 6850 else if (dev->sensorcfg->rgb_order[CL_GREEN] == 1) 6851 { 6852 myp1 = pGreen; 6853 myp2 = pRed; 6854 myp3 = pBlue; 6855 } 6856 else 6857 { 6858 myp1 = pBlue; 6859 myp2 = pRed; 6860 myp3 = pGreen; 6861 } 6862 6863 while (dots > 0) 6864 { 6865 Value = 6866 min (((*myp1 + *(line_size + myp1)) / 2) + *myp2 + *myp3, 0xff); 6867 6868 *buffer = (v1600 == NULL) ? _B0 (Value) : *(v1600 + Value); 6869 6870 buffer++; 6871 myp1 += 3; 6872 myp2 += 3; 6873 myp3 += 3; 6874 dots--; 6875 } 6876 } 6877} 6878 6879static void 6880Triplet_Compose_LRes (SANE_Byte * pRed, SANE_Byte * pGreen, SANE_Byte * pBlue, 6881 SANE_Byte * buffer, SANE_Int dots) 6882{ 6883 SANE_Int Value; 6884 SANE_Int Channel_size; 6885 SANE_Int max_value; 6886 6887 DBG (DBG_FNC, 6888 "> Triplet_Compose_LRes(*pRed, *pGreen, *pBlue, *buffer, dots=%i):\n", 6889 dots); 6890 6891 Channel_size = (scan2.depth > 8) ? 2 : 1; 6892 max_value = (1 << scan2.depth) - 1; 6893 6894 /*bf59 */ 6895 while (dots > 0) 6896 { 6897 Value = 6898 data_lsb_get (pRed, Channel_size) + data_lsb_get (pGreen, 6899 Channel_size) + 6900 data_lsb_get (pBlue, Channel_size); 6901 6902 Value = min (Value, max_value); 6903 6904 if (v1600 != NULL) 6905 { 6906 if (scan2.depth > 8) 6907 Value = (*(v1600 + (Value >> 8)) << 8) | _B0 (Value); 6908 else 6909 Value = _B0 (*(v1600 + Value)); 6910 } 6911 6912 data_lsb_set (buffer, Value, Channel_size); 6913 6914 buffer += Channel_size; 6915 pRed += Channel_size * 3; 6916 pGreen += Channel_size * 3; 6917 pBlue += Channel_size * 3; 6918 dots--; 6919 } 6920} 6921 6922static void 6923Triplet_Colour_Order (struct st_device *dev, SANE_Byte * pRed, 6924 SANE_Byte * pGreen, SANE_Byte * pBlue, 6925 SANE_Byte * buffer, SANE_Int Width) 6926{ 6927 SANE_Int Value; 6928 6929 DBG (DBG_FNC, 6930 "> Triplet_Colour_Order(*pRed, *pGreen, *pBlue, *buffer, Width=%i):\n", 6931 Width); 6932 6933 if (scan2.depth > 8) 6934 { 6935 Width = Width / 2; 6936 while (Width > 0) 6937 { 6938 Value = data_lsb_get (pRed, 2); 6939 data_lsb_set (buffer, Value, 2); 6940 6941 Value = data_lsb_get (pGreen, 2); 6942 data_lsb_set (buffer + 2, Value, 2); 6943 6944 Value = data_lsb_get (pBlue, 2); 6945 data_lsb_set (buffer + 4, Value, 2); 6946 6947 pRed += 6; 6948 pGreen += 6; 6949 pBlue += 6; 6950 buffer += 6; 6951 Width--; 6952 } 6953 } 6954 else 6955 { 6956 SANE_Int Colour; 6957 6958 if (dev->sensorcfg->rgb_order[CL_RED] == 1) 6959 Colour = CL_RED; 6960 else if (dev->sensorcfg->rgb_order[CL_GREEN] == 1) 6961 Colour = CL_GREEN; 6962 else 6963 Colour = CL_BLUE; 6964 6965 while (Width > 0) 6966 { 6967 switch (Colour) 6968 { 6969 case CL_RED: 6970 *buffer = (*pRed + *(pRed + line_size)) / 2; 6971 *(buffer + 1) = *pGreen; 6972 *(buffer + 2) = *pBlue; 6973 break; 6974 case CL_GREEN: 6975 *buffer = *pRed; 6976 *(buffer + 1) = ((*pGreen + *(pGreen + line_size)) / 2); 6977 *(buffer + 2) = *pBlue; 6978 break; 6979 case CL_BLUE: 6980 *buffer = *pRed; 6981 *(buffer + 1) = *pGreen; 6982 *(buffer + 2) = ((*pBlue + *(pBlue + line_size)) / 2); 6983 break; 6984 } 6985 6986 pRed += 3; 6987 pGreen += 3; 6988 pBlue += 3; 6989 buffer += 3; 6990 6991 Width--; 6992 } 6993 } 6994} 6995 6996static void 6997Triplet_Colour_HRes (SANE_Byte * pRed1, SANE_Byte * pGreen1, 6998 SANE_Byte * pBlue1, SANE_Byte * pRed2, 6999 SANE_Byte * pGreen2, SANE_Byte * pBlue2, 7000 SANE_Byte * buffer, SANE_Int Width) 7001{ 7002 SANE_Int Value; 7003 SANE_Int channel_size; 7004 SANE_Int c; 7005 SANE_Byte *pPointers[6]; 7006 7007 pPointers[0] = pRed1; 7008 pPointers[1] = pGreen1; 7009 pPointers[2] = pBlue1; 7010 7011 pPointers[3] = pRed2; 7012 pPointers[4] = pGreen2; 7013 pPointers[5] = pBlue2; 7014 7015 DBG (DBG_FNC, 7016 "> Triplet_Colour_HRes(*pRed1, *pGreen1, *pBlue1, *pRed2, *pGreen2, *pBlue2, *buffer, Width=%i):\n", 7017 Width); 7018 7019 channel_size = (scan2.depth > 8) ? 2 : 1; 7020 7021 Width = Width / 2; 7022 while (Width > 0) 7023 { 7024 for (c = 0; c < 6; c++) 7025 { 7026 Value = data_lsb_get (pPointers[c], channel_size); 7027 data_lsb_set (buffer, Value, channel_size); 7028 7029 pPointers[c] += (6 * channel_size); 7030 buffer += (channel_size); 7031 } 7032 Width--; 7033 } 7034} 7035 7036static void 7037Triplet_Colour_LRes (SANE_Int Width, SANE_Byte * Buffer, 7038 SANE_Byte * pChannel1, SANE_Byte * pChannel2, 7039 SANE_Byte * pChannel3) 7040{ 7041 /* 7042 05F0FA4C 04EBAE4A /CALL to Assumed StdFunc6 from hpgt3970.04EBAE45 7043 05F0FA50 00234FF8 |Arg1 = 00234FF8 pChannel3 7044 05F0FA54 002359EF |Arg2 = 002359EF pChannel2 7045 05F0FA58 002363E6 |Arg3 = 002363E6 pChannel1 7046 05F0FA5C 05D10048 |Arg4 = 05D10048 Buffer 7047 05F0FA60 00000352 |Arg5 = 00000352 Width 7048 */ 7049 7050 /* Esta funcion une los tres canales de color en un triplete 7051 Inicialmente cada color está separado en 3 buffers apuntados 7052 por pChannel1 ,2 y 3 7053 */ 7054 SANE_Int Value; 7055 SANE_Int channel_size; 7056 SANE_Int c; 7057 SANE_Byte *pChannels[3]; 7058 7059 pChannels[0] = pChannel3; 7060 pChannels[1] = pChannel2; 7061 pChannels[2] = pChannel1; 7062 7063 DBG (DBG_FNC, "> Triplet_Colour_LRes(Width=%i, *Buffer2, *p1, *p2, *p3):\n", 7064 Width); 7065 7066 channel_size = (scan2.depth > 8) ? 2 : 1; 7067 while (Width > 0) 7068 { 7069 /* ba74 */ 7070 for (c = 0; c < 3; c++) 7071 { 7072 Value = data_lsb_get (pChannels[c], channel_size); 7073 data_lsb_set (Buffer, Value, channel_size); 7074 7075 pChannels[c] += channel_size; 7076 Buffer += channel_size; 7077 } 7078 Width--; 7079 } 7080} 7081 7082static SANE_Int 7083Read_ResizeBlock (struct st_device *dev, SANE_Byte * buffer, 7084 SANE_Int buffer_size, SANE_Int * transferred) 7085{ 7086 /*The Beach 7087 buffer = FA7C 05E30048 7088 buffer_size = FA80 0000F906 7089 */ 7090 7091 SANE_Int rst = ERROR; /* fa68 */ 7092 SANE_Int lfa54; 7093 SANE_Int lfa58; 7094 SANE_Byte *pP1; /* fa5c */ 7095 SANE_Byte *pP2; /* fa60 */ 7096 SANE_Int bOk; 7097 struct st_resize *rz = dev->Resize; 7098 7099 /* fa74 = Resize->resolution_y */ 7100 /* fa70 = Resize->resolution_x */ 7101 /* fa64 = scan2.resolution_y */ 7102 /* fa6c = scan2.resolution_x */ 7103 7104 DBG (DBG_FNC, 7105 "+ Read_ResizeBlock(*buffer, buffer_size=%i, *transferred):\n", 7106 buffer_size); 7107 7108 if (rz->type == RSZ_DECREASE) 7109 { 7110 lfa58 = 0; 7111 do 7112 { 7113 bOk = 1; 7114 if (arrangeline2 == FIX_BY_SOFT) 7115 { 7116 if (scan2.colormode == CM_COLOR) 7117 rst = Arrange_Colour (dev, rz->v3624, line_size, transferred); 7118 else 7119 rst = 7120 Arrange_NonColour (dev, rz->v3624, line_size, transferred); 7121 } 7122 else 7123 rst = Read_Block (dev, line_size, rz->v3624, transferred); 7124 7125 /*f2df */ 7126 Resize_Decrease (rz->v362c, rz->resolution_x, rz->towidth, 7127 rz->v3624, scan2.resolution_x, rz->fromwidth, 7128 rz->mode); 7129 rz->rescount += rz->resolution_y; 7130 7131 if (rz->rescount > scan2.resolution_y) 7132 { 7133 /*f331 */ 7134 rz->rescount -= scan2.resolution_y; 7135 if (scan2.depth == 8) 7136 { 7137 /* f345 */ 7138 pP1 = rz->v3628; 7139 pP2 = rz->v362c; 7140 if (rz->mode == RSZ_LINEART) 7141 { 7142 /* f36b */ 7143 SANE_Int bit = 0; 7144 SANE_Byte *pP3 = rz->v362c; 7145 SANE_Int value; 7146 7147 *buffer = 0; 7148 lfa54 = 0; 7149 while (lfa54 < rz->towidth) 7150 { 7151 if (bit == 8) 7152 { 7153 buffer++; 7154 *buffer = 0; 7155 pP1++; 7156 bit = 0; 7157 pP3++; 7158 } 7159 7160 value = 7161 ((*pP1 & (0x80 >> bit)) != 0) ? rz->rescount : 0; 7162 7163 if ((*pP3 & (0x80 >> bit)) != 0) 7164 value += (scan2.resolution_y - rz->rescount); 7165 7166 if (value > rz->resolution_y) 7167 *buffer |= (0x80 >> bit); 7168 7169 bit++; 7170 lfa54++; 7171 } 7172 } 7173 else 7174 { 7175 /* f414 */ 7176 lfa54 = 0; 7177 while (lfa54 < rz->bytesperline) 7178 { 7179 *buffer = 7180 _B0 ((((scan2.resolution_y - 7181 rz->rescount) * *pP2) + 7182 (*pP1 * rz->rescount)) / 7183 scan2.resolution_y); 7184 pP1++; 7185 pP2++; 7186 buffer++; 7187 lfa54++; 7188 } 7189 } 7190 } 7191 else 7192 { 7193 /* f47d */ 7194 lfa54 = 0; 7195 pP1 = rz->v3628; 7196 pP2 = rz->v362c; 7197 7198 if ((rz->bytesperline & 0xfffffffe) > 0) 7199 { 7200 SANE_Int value; 7201 do 7202 { 7203 value = 7204 (((scan2.resolution_y - 7205 rz->rescount) * data_lsb_get (pP2, 7206 2)) + 7207 (data_lsb_get (pP1, 2) * rz->rescount)) / 7208 scan2.resolution_y; 7209 data_lsb_set (buffer, value, 2); 7210 7211 buffer += 2; 7212 pP1 += 2; 7213 pP2 += 2; 7214 lfa54++; 7215 } 7216 while (lfa54 < (rz->bytesperline / 2)); 7217 } 7218 } 7219 } 7220 else 7221 bOk = 0; 7222 /* f4fd f502 */ 7223 pP1 = rz->v3628; 7224 /* swap pointers */ 7225 rz->v3628 = rz->v362c; 7226 rz->v362c = pP1; 7227 } 7228 while (bOk == 0); 7229 } 7230 else 7231 { 7232 /*f530 */ 7233 SANE_Int lfa68; 7234 SANE_Int transferred; 7235 SANE_Int channel_size; 7236 7237 rz->rescount += scan2.resolution_y; 7238 lfa58 = 0; 7239 if (rz->rescount > rz->resolution_y) 7240 { 7241 lfa68 = 1; 7242 rz->rescount -= rz->resolution_y; 7243 } 7244 else 7245 lfa68 = 0; 7246 7247 pP1 = rz->v3628; 7248 pP2 = rz->v362c; 7249 7250 if (rz->mode == RSZ_LINEART) 7251 { 7252 /*f592 */ 7253 *buffer = 0; 7254 7255 if (rz->towidth > 0) 7256 { 7257 SANE_Int mask, mres; 7258 /* lfa60 = rz->resolution_y */ 7259 /* lfa7c = rz->resolution_y / 2 */ 7260 7261 for (lfa54 = 0; lfa54 < rz->towidth; lfa54++) 7262 { 7263 mask = 0x80 >> lfa58; 7264 7265 mres = ((mask & *pP1) != 0) ? rz->rescount : 0; 7266 7267 if ((mask & *pP2) != 0) 7268 mres += (rz->resolution_y - rz->rescount); 7269 7270 if (mres > (rz->resolution_y / 2)) 7271 *buffer = *buffer | mask; 7272 7273 lfa58++; 7274 if (lfa58 == 8) 7275 { 7276 lfa58 = 0; 7277 buffer++; 7278 pP1++; 7279 pP2++; 7280 *buffer = 0; 7281 } 7282 } 7283 } 7284 } 7285 else 7286 { 7287 /*f633 */ 7288 channel_size = (scan2.depth > 8) ? 2 : 1; 7289 7290 if (rz->rescount < scan2.resolution_y) 7291 { 7292 if (rz->bytesperline != 0) 7293 { 7294 SANE_Int value; 7295 7296 for (lfa54 = 0; lfa54 < rz->bytesperline; lfa54++) 7297 { 7298 value = 7299 (((scan2.resolution_y - 7300 rz->rescount) * data_lsb_get (pP2, 7301 channel_size)) + 7302 (rz->rescount * data_lsb_get (pP1, channel_size))) / 7303 scan2.resolution_y; 7304 data_lsb_set (buffer, value, channel_size); 7305 7306 pP1 += channel_size; 7307 pP2 += channel_size; 7308 buffer += channel_size; 7309 } 7310 } 7311 } 7312 else 7313 memcpy (buffer, rz->v3628, rz->bytesperline); /*f6a8 */ 7314 } 7315 7316 /*f736 */ 7317 if (lfa68 != 0) 7318 { 7319 SANE_Byte *temp; 7320 7321 if (arrangeline2 == FIX_BY_SOFT) 7322 { 7323 /*f74b */ 7324 if (scan2.colormode == CM_COLOR) 7325 rst = 7326 Arrange_Colour (dev, rz->v3624, line_size, &transferred); 7327 else 7328 rst = 7329 Arrange_NonColour (dev, rz->v3624, line_size, &transferred); 7330 } 7331 else 7332 rst = Read_Block (dev, line_size, rz->v3624, &transferred); /*f77a */ 7333 7334 /*f78c */ 7335 /* swap buffers */ 7336 temp = rz->v3628; 7337 rz->v3628 = rz->v362c; 7338 rz->v362c = temp; 7339 7340 Resize_Increase (temp, rz->resolution_x, rz->towidth, rz->v3624, 7341 scan2.resolution_x, rz->fromwidth, rz->mode); 7342 } 7343 else 7344 rst = OK; 7345 } 7346 7347 DBG (DBG_FNC, "- Read_ResizeBlock(*transferred=%i): %i\n", *transferred, 7348 rst); 7349 7350 return rst; 7351} 7352 7353static void 7354Split_into_12bit_channels (SANE_Byte * destino, SANE_Byte * fuente, 7355 SANE_Int size) 7356{ 7357 /* 7358 Each letter represents a bit 7359 abcdefgh 12345678 lmnopqrs << before splitting 7360 [efgh1234 0000abcd] [lmnopqrs 00005678] << after splitting, in memory 7361 [0000abcd efgh1234] [00005678 lmnopqrs] << resulting channels 7362 */ 7363 7364 DBG (DBG_FNC, "> Split_into_12bit_channels(*destino, *fuente, size=%i\n", 7365 size); 7366 7367 if ((destino != NULL) && (fuente != NULL)) 7368 { 7369 if ((size - (size & 0x03)) != 0) 7370 { 7371 SANE_Int C; 7372 7373 C = (size - (size & 0x03) + 3) / 4; 7374 do 7375 { 7376 *destino = _B0 ((*(fuente + 1) >> 4) + (*fuente << 4)); 7377 *(destino + 1) = _B0 (*fuente >> 4); 7378 *(destino + 2) = _B0 (*(fuente + 2)); 7379 *(destino + 3) = *(fuente + 1) & 0x0f; 7380 destino += 4; 7381 fuente += 3; 7382 C--; 7383 } 7384 while (C > 0); 7385 } 7386 7387 /**/ if ((size & 0x03) != 0) 7388 { 7389 *destino = _B0 ((*(fuente + 1) >> 4) + (*fuente << 4)); 7390 *(destino + 1) = _B0 (*fuente >> 4); 7391 } 7392 } 7393} 7394 7395static SANE_Int 7396Read_NonColor_Block (struct st_device *dev, SANE_Byte * buffer, 7397 SANE_Int buffer_size, SANE_Byte ColorMode, 7398 SANE_Int * transferred) 7399{ 7400 /* FA50 05DA0048 buffer 7401 FA54 0000F906 buffer_size 7402 FA58 00 ColorMode 7403 */ 7404 7405 SANE_Int rst = OK; 7406 SANE_Int lfa38 = 0; 7407 SANE_Byte *gamma = v1600; 7408 SANE_Int block_bytes_per_line; 7409 SANE_Int mysize; 7410 SANE_Byte *mybuffer; 7411 7412 DBG (DBG_FNC, 7413 "+ Read_NonColor_Block(*buffer, buffer_size=%i, ColorMode=%s):\n", 7414 buffer_size, dbg_colour (ColorMode)); 7415 7416 if (ColorMode != CM_GRAY) 7417 { 7418 /* Lineart mode */ 7419 if ((lineart_width & 7) != 0) 7420 lfa38 = 8 - (lineart_width & 7); 7421 block_bytes_per_line = (lineart_width + 7) / 8; 7422 } 7423 else 7424 block_bytes_per_line = line_size; 7425 /*61b2 */ 7426 7427 mysize = (buffer_size / block_bytes_per_line) * bytesperline; 7428 mybuffer = (SANE_Byte *) malloc (mysize * sizeof (SANE_Byte)); /*fa40 */ 7429 7430 if (mybuffer != NULL) 7431 { 7432 SANE_Int LinesCount; 7433 SANE_Int mysize4lines; 7434 SANE_Byte *pBuffer = buffer; 7435 SANE_Byte *pImage = NULL; /* fa30 */ 7436 SANE_Int puntero; 7437 SANE_Int value; 7438 7439 do 7440 { 7441 mysize4lines = 7442 (mysize <= 7443 dev->Reading->Size4Lines) ? mysize : dev->Reading->Size4Lines; 7444 LinesCount = mysize4lines / bytesperline; 7445 7446 if (ColorMode == CM_GRAY) 7447 { 7448 if (scan2.depth == 12) 7449 { 7450 /* 633b */ 7451 /*GRAY Bit mode 12 */ 7452 rst = 7453 Scan_Read_BufferA (dev, (mysize4lines * 3) / 4, 0, 7454 mybuffer, transferred); 7455 if (rst == OK) 7456 { 7457 pImage = mybuffer; 7458 pBuffer += LinesCount * block_bytes_per_line; 7459 while (LinesCount > 0) 7460 { 7461 Split_into_12bit_channels (mybuffer, pImage, 7462 line_size); 7463 pImage += (bytesperline * 3) / 4; 7464 LinesCount--; 7465 } 7466 } 7467 else 7468 break; 7469 } 7470 else 7471 { 7472 /* grayscale 8 and 16 bits */ 7473 7474 SANE_Int channel_size; 7475 7476 rst = 7477 Scan_Read_BufferA (dev, mysize4lines, 0, mybuffer, 7478 transferred); 7479 7480 if (rst == OK) 7481 { 7482 channel_size = (scan2.depth > 8) ? 2 : 1; 7483 7484 pImage = mybuffer; 7485 7486 /* No gamma tables */ 7487 while (LinesCount > 0) 7488 { 7489 if (line_size > 0) 7490 { 7491 puntero = 0; 7492 do 7493 { 7494 value = 7495 data_lsb_get (pImage + puntero, 7496 channel_size); 7497 7498 if (gamma != NULL) 7499 value += 7500 *gamma << (8 * (channel_size - 1)); 7501 7502 data_lsb_set (pBuffer, value, channel_size); 7503 7504 pBuffer += channel_size; 7505 puntero += channel_size; 7506 } 7507 while (puntero < line_size); 7508 } 7509 pImage += bytesperline; 7510 LinesCount--; 7511 } 7512 } 7513 else 7514 break; 7515 } 7516 } 7517 else 7518 { 7519 /*6429 */ 7520 /* LINEART */ 7521 SANE_Int desp; 7522 rst = 7523 Scan_Read_BufferA (dev, mysize4lines, 0, mybuffer, 7524 transferred); 7525 if (rst == OK) 7526 { 7527 pImage = mybuffer; 7528 while (LinesCount > 0) 7529 { 7530 if (lineart_width > 0) 7531 { 7532 desp = 0; 7533 do 7534 { 7535 if ((desp % 7) == 0) 7536 *pBuffer = 0; 7537 7538 /* making a byte bit per bit */ 7539 *pBuffer = *pBuffer << 1; 7540 7541 /* bit 1 if data is under thresholdh value */ 7542 if (*(pImage + desp) >= binarythresholdh) /* binarythresholdh = 0x0c */ 7543 *pBuffer = *pBuffer | 1; 7544 7545 desp++; 7546 if ((desp % 7) == 0) 7547 pBuffer++; 7548 7549 } 7550 while (desp < lineart_width); 7551 } 7552 7553 if (lfa38 != 0) 7554 { 7555 *pBuffer = (*pBuffer << lfa38); 7556 pBuffer++; 7557 } 7558 /* 64b0 */ 7559 pImage += bytesperline; 7560 LinesCount--; 7561 } 7562 } 7563 else 7564 break; 7565 } 7566 /* 64c0 */ 7567 mysize -= mysize4lines; 7568 } 7569 while ((mysize > 0) && (dev->status->cancel == FALSE)); 7570 7571 free (mybuffer); 7572 } 7573 else 7574 rst = ERROR; 7575 7576 DBG (DBG_FNC, "- Read_NonColor_Block(*transferred=%i): %i\n", *transferred, 7577 rst); 7578 7579 return rst; 7580} 7581 7582static SANE_Int 7583Read_Block (struct st_device *dev, SANE_Int buffer_size, SANE_Byte * buffer, 7584 SANE_Int * transferred) 7585{ 7586 /* 7587 SANE_Int buffer_size fa80 7588 SANE_Byte *buffer fa7c 7589 */ 7590/* 7591scan2: 759204F0155C 01 08 00 02 03 00 58 02 ..X 759304F01564 58 02 58 02 C5 00 00 00 XXÅ... 759404F0156C B4 07 00 00 8B 01 00 00 ´.... 759504F01574 10 06 00 00 EC 13 00 00 ..ì.. 759604F0157C B2 07 00 00 B4 07 00 00 ²..´.. 759704F01584 CF 08 00 00 Ï.. 7598 7599arrangeline2 = 1 7600*/ 7601 SANE_Int rst, LinesCount; 7602 SANE_Int mysize; 7603 SANE_Byte *readbuffer = NULL; 7604 SANE_Byte *pImage = NULL; 7605 7606 DBG (DBG_FNC, "+ Read_Block(buffer_size=%i, *buffer):\n", buffer_size); 7607 7608 rst = ERROR; 7609 *transferred = 0; 7610 7611 if ((scan2.colormode != CM_COLOR) && (scan2.channel == 3) 7612 && (arrangeline2 != FIX_BY_SOFT)) 7613 { 7614 /*6510 */ 7615 return Read_NonColor_Block (dev, buffer, buffer_size, scan2.colormode, 7616 transferred); 7617 } 7618 7619 /*6544 */ 7620 mysize = (buffer_size / line_size) * bytesperline; 7621 readbuffer = (SANE_Byte *) malloc (mysize * sizeof (SANE_Byte)); 7622 pImage = buffer; 7623 7624 if (readbuffer != NULL) 7625 { 7626 do 7627 { 7628 buffer_size = 7629 (dev->Reading->Size4Lines < 7630 mysize) ? dev->Reading->Size4Lines : mysize; 7631 LinesCount = buffer_size / bytesperline; 7632 7633 if (scan2.depth == 12) 7634 { 7635 rst = 7636 Scan_Read_BufferA (dev, buffer_size, 0, readbuffer, 7637 transferred); 7638 if (rst == OK) 7639 { 7640 if (LinesCount > 0) 7641 { 7642 SANE_Byte *destino, *fuente; 7643 destino = buffer; 7644 fuente = readbuffer; 7645 do 7646 { 7647 Split_into_12bit_channels (destino, fuente, 7648 line_size); 7649 destino += line_size; 7650 fuente += (bytesperline * 3) / 4; 7651 LinesCount--; 7652 } 7653 while (LinesCount > 0); 7654 } 7655 } 7656 else 7657 break; 7658 } 7659 else 7660 { 7661 /*65d9 */ 7662 rst = 7663 Scan_Read_BufferA (dev, buffer_size, 0, readbuffer, 7664 transferred); 7665 if (rst == OK) 7666 { 7667 memcpy (pImage, readbuffer, *transferred); 7668 7669 /* apply white shading correction */ 7670 if ((RTS_Debug->wshading == TRUE) 7671 && (scan2.scantype == ST_NORMAL)) 7672 WShading_Emulate (pImage, &wshading->ptr, *transferred, 7673 scan2.depth); 7674 7675 pImage += *transferred; 7676 } 7677 else 7678 break; 7679 } 7680 /*6629 */ 7681 mysize -= buffer_size; 7682 } 7683 while ((mysize > 0) && (dev->status->cancel == FALSE)); 7684 7685 free (readbuffer); 7686 } 7687 7688 DBG (DBG_FNC, "- Read_Block(*transferred=%i): %i\n", *transferred, rst); 7689 7690 return rst; 7691} 7692 7693static SANE_Int 7694Scan_Read_BufferA (struct st_device *dev, SANE_Int buffer_size, SANE_Int arg2, 7695 SANE_Byte * pBuffer, SANE_Int * bytes_transferred) 7696{ 7697 SANE_Int rst = OK; 7698 SANE_Byte *ptBuffer = NULL; 7699 SANE_Byte *ptImg = NULL; 7700 struct st_readimage *rd = dev->Reading; 7701 7702 DBG (DBG_FNC, 7703 "+ Scan_Read_BufferA(buffer_size=%i, arg2, *pBuffer, *bytes_transferred):\n", 7704 buffer_size); 7705 7706 (void) arg2; /* silence gcc */ 7707 *bytes_transferred = 0; 7708 7709 if (pBuffer != NULL) 7710 { 7711 ptBuffer = pBuffer; 7712 7713 while ((buffer_size > 0) && (rst == OK) 7714 && (dev->status->cancel == FALSE)) 7715 { 7716 /* Check if we've already started */ 7717 if (rd->Starting == TRUE) 7718 { 7719 /* Get channels per dot and channel's size in bytes */ 7720 SANE_Byte data; 7721 7722 rd->Channels_per_dot = 1; 7723 if (Read_Byte (dev->usb_handle, 0xe812, &data) == OK) 7724 { 7725 data = data >> 6; 7726 if (data != 0) 7727 rd->Channels_per_dot = data; 7728 } 7729 7730 rd->Channel_size = 1; 7731 if (Read_Byte (dev->usb_handle, 0xee0b, &data) == OK) 7732 if (((data & 0x40) != 0) && ((data & 0x08) == 0)) 7733 rd->Channel_size = 2; 7734 7735 rd->RDStart = rd->DMABuffer; 7736 rd->RDSize = 0; 7737 rd->DMAAmount = 0; 7738 rd->Starting = FALSE; 7739 } 7740 7741 /* Is there any data to read from scanner? */ 7742 if ((rd->ImageSize > 0) && (rd->RDSize == 0)) 7743 { 7744 /* Try to read from scanner all possible data to fill DMABuffer */ 7745 if (rd->RDSize < rd->DMABufferSize) 7746 { 7747 SANE_Int iAmount, dofree; 7748 7749 /* Check if we have already notify buffer size */ 7750 if (rd->DMAAmount <= 0) 7751 { 7752 /* Initially I suppose that I can read all image */ 7753 iAmount = min (rd->ImageSize, rd->Max_Size); 7754 rd->DMAAmount = 7755 ((RTS_Debug->dmasetlength * 2) / iAmount) * iAmount; 7756 rd->DMAAmount = min (rd->DMAAmount, rd->ImageSize); 7757 Reading_BufferSize_Notify (dev, 0, rd->DMAAmount); 7758 iAmount = min (iAmount, rd->DMABufferSize - rd->RDSize); 7759 } 7760 else 7761 { 7762 iAmount = min (rd->DMAAmount, rd->ImageSize); 7763 iAmount = min (iAmount, rd->Max_Size); 7764 } 7765 7766 /* Allocate buffer to read image if it's necessary */ 7767 if ((rd->RDSize == 0) && (iAmount <= buffer_size)) 7768 { 7769 ptImg = ptBuffer; 7770 dofree = FALSE; 7771 } 7772 else 7773 { 7774 ptImg = 7775 (SANE_Byte *) malloc (iAmount * sizeof (SANE_Byte)); 7776 dofree = TRUE; 7777 } 7778 7779 if (ptImg != NULL) 7780 { 7781 /* We must wait for scanner to get data */ 7782 SANE_Int opStatus, sc; 7783 7784 sc = (iAmount < rd->Max_Size) ? TRUE : FALSE; 7785 opStatus = Reading_Wait (dev, rd->Channels_per_dot, 7786 rd->Channel_size, 7787 iAmount, 7788 &rd->Bytes_Available, 60, sc); 7789 7790 /* If something fails, perhaps we can read some bytes... */ 7791 if (opStatus != OK) 7792 { 7793 if (rd->Bytes_Available > 0) 7794 iAmount = rd->Bytes_Available; 7795 else 7796 rst = ERROR; 7797 } 7798 7799 if (rst == OK) 7800 { 7801 /* Try to read from scanner */ 7802 SANE_Int transferred = 0; 7803 opStatus = 7804 Bulk_Operation (dev, BLK_READ, iAmount, ptImg, 7805 &transferred); 7806 7807 DBG (DBG_FNC, 7808 "> Scan_Read_BufferA: Bulk read %i bytes\n", 7809 transferred); 7810 7811 /*if something fails may be we can read some bytes */ 7812 iAmount = (SANE_Int) transferred; 7813 if (iAmount != 0) 7814 { 7815 /* Lets copy data into DMABuffer if it's necessary */ 7816 if (ptImg != ptBuffer) 7817 { 7818 SANE_Byte *ptDMABuffer; 7819 7820 ptDMABuffer = rd->RDStart + rd->RDSize; 7821 if ((ptDMABuffer - rd->DMABuffer) >= 7822 rd->DMABufferSize) 7823 ptDMABuffer -= rd->DMABufferSize; 7824 7825 if ((ptDMABuffer + iAmount) >= 7826 (rd->DMABuffer + rd->DMABufferSize)) 7827 { 7828 SANE_Int rest = 7829 iAmount - (rd->DMABufferSize - 7830 (ptDMABuffer - 7831 rd->DMABuffer)); 7832 memcpy (ptDMABuffer, ptImg, 7833 iAmount - rest); 7834 memcpy (rd->DMABuffer, 7835 ptImg + (iAmount - rest), rest); 7836 } 7837 else 7838 memcpy (ptDMABuffer, ptImg, iAmount); 7839 rd->RDSize += iAmount; 7840 } 7841 else 7842 { 7843 *bytes_transferred += iAmount; 7844 buffer_size -= iAmount; 7845 } 7846 7847 rd->DMAAmount -= iAmount; 7848 rd->ImageSize -= iAmount; 7849 } 7850 else 7851 rst = ERROR; 7852 } 7853 7854 /* Lets free buffer */ 7855 if (dofree == TRUE) 7856 { 7857 free (ptImg); 7858 ptImg = NULL; 7859 } 7860 } 7861 else 7862 rst = ERROR; 7863 } 7864 } 7865 7866 /* is there any data read from scanner? */ 7867 if (rd->RDSize > 0) 7868 { 7869 /* Add to the given buffer as many bytes as possible */ 7870 SANE_Int iAmount; 7871 7872 iAmount = min (buffer_size, rd->RDSize); 7873 if ((rd->RDStart + iAmount) >= 7874 (rd->DMABuffer + rd->DMABufferSize)) 7875 { 7876 SANE_Int rest = 7877 rd->DMABufferSize - (rd->RDStart - rd->DMABuffer); 7878 memcpy (ptBuffer, rd->RDStart, rest); 7879 memcpy (ptBuffer + rest, rd->DMABuffer, iAmount - rest); 7880 rd->RDStart = rd->DMABuffer + (iAmount - rest); 7881 } 7882 else 7883 { 7884 memcpy (ptBuffer, rd->RDStart, iAmount); 7885 rd->RDStart += iAmount; 7886 } 7887 7888 ptBuffer += iAmount; 7889 rd->RDSize -= iAmount; 7890 buffer_size -= iAmount; 7891 *bytes_transferred += iAmount; 7892 7893 /* if there isn't any data in DMABuffer we can point RDStart 7894 to the beginning of DMABuffer */ 7895 if (rd->RDSize == 0) 7896 rd->RDStart = rd->DMABuffer; 7897 } 7898 7899 /* in case of all data is read we return OK with bytes_transferred = 0 */ 7900 if ((*bytes_transferred == 0) 7901 || ((rd->RDSize == 0) && (rd->ImageSize == 0))) 7902 break; 7903 } 7904 7905 if (rst == ERROR) 7906 RTS_DMA_Cancel (dev); 7907 } 7908 7909 DBG (DBG_FNC, "-> *bytes_transferred=%i\n", *bytes_transferred); 7910 DBG (DBG_FNC, "-> Reading->ImageSize=%i\n", rd->ImageSize); 7911 DBG (DBG_FNC, "-> Reading->DMAAmount=%i\n", rd->DMAAmount); 7912 DBG (DBG_FNC, "-> Reading->RDSize =%i\n", rd->RDSize); 7913 7914 DBG (DBG_FNC, "- Scan_Read_BufferA: %i\n", rst); 7915 7916 return rst; 7917} 7918 7919static SANE_Int 7920Reading_BufferSize_Get (struct st_device *dev, SANE_Byte channels_per_dot, 7921 SANE_Int channel_size) 7922{ 7923 /* returns the amount of bytes in scanner's buffer ready to be read */ 7924 7925 SANE_Int rst; 7926 7927 DBG (DBG_FNC, 7928 "+ Reading_BufferSize_Get(channels_per_dot=%i, channel_size=%i):\n", 7929 channels_per_dot, channel_size); 7930 7931 rst = 0; 7932 7933 if (channel_size > 0) 7934 { 7935 SANE_Int myAmount; 7936 7937 if (channels_per_dot < 1) 7938 { 7939 /* read channels per dot from registers */ 7940 if (Read_Byte (dev->usb_handle, 0xe812, &channels_per_dot) == OK) 7941 channels_per_dot = _B0 (channels_per_dot >> 6); 7942 7943 if (channels_per_dot == 0) 7944 channels_per_dot++; 7945 } 7946 7947 if (Read_Integer (dev->usb_handle, 0xef16, &myAmount) == OK) 7948 rst = ((channels_per_dot * 32) / channel_size) * myAmount; 7949 } 7950 7951 DBG (DBG_FNC, "- Reading_BufferSize_Get: %i bytes\n", rst); 7952 7953 return rst; 7954} 7955 7956static SANE_Int 7957Lamp_Warmup (struct st_device *dev, SANE_Byte * Regs, SANE_Int lamp, 7958 SANE_Int resolution) 7959{ 7960 SANE_Int rst = OK; 7961 7962 DBG (DBG_FNC, "+ Lamp_Warmup(*Regs, lamp=%i, resolution=%i)\n", lamp, 7963 resolution); 7964 7965 if (Regs != NULL) 7966 { 7967 SANE_Byte flb_lamp, tma_lamp; 7968 SANE_Int overdrivetime; 7969 7970 Lamp_Status_Get (dev, &flb_lamp, &tma_lamp); 7971 7972 /* ensure that selected lamp is switched on */ 7973 if (lamp == FLB_LAMP) 7974 { 7975 overdrivetime = RTS_Debug->overdrive_flb; 7976 7977 if (flb_lamp == 0) 7978 { 7979 /* FLB-Lamp is turned off, lets turn on */ 7980 Lamp_Status_Set (dev, Regs, TRUE, FLB_LAMP); 7981 waitforpwm = TRUE; 7982 } 7983 } 7984 else 7985 { 7986 /* is tma device attached to scanner ? */ 7987 if (RTS_isTmaAttached (dev) == TRUE) 7988 { 7989 overdrivetime = RTS_Debug->overdrive_ta; 7990 7991 if (tma_lamp == 0) 7992 { 7993 /* tma lamp is turned off */ 7994 Lamp_Status_Set (dev, Regs, FALSE, TMA_LAMP); 7995 waitforpwm = TRUE; 7996 } 7997 } 7998 else 7999 rst = ERROR; 8000 } 8001 8002 /* perform warmup process */ 8003 if (rst == OK) 8004 { 8005 Lamp_PWM_Setup (dev, lamp); 8006 8007 if (waitforpwm == TRUE) 8008 { 8009 /*Lamp_PWM_DutyCycle_Set(dev, (lamp == TMA_LAMP)? 0x0e : 0x00); */ 8010 8011 if (RTS_Debug->warmup == TRUE) 8012 { 8013 long ticks = GetTickCount () + overdrivetime; 8014 8015 DBG (DBG_VRB, "- Lamp Warmup process. Please wait...\n"); 8016 8017 dev->status->warmup = TRUE; 8018 8019 while (GetTickCount () <= ticks) 8020 usleep (1000 * 200); 8021 8022 Lamp_PWM_CheckStable (dev, resolution, lamp); 8023 8024 } 8025 else 8026 DBG (DBG_VRB, "- Lamp Warmup process disabled.\n"); 8027 } 8028 8029 /*Lamp_PWM_Setup(dev, lamp); 8030 8031 if (waitforpwm == TRUE) 8032 { 8033 if (RTS_Debug->warmup == TRUE) 8034 Lamp_PWM_CheckStable(dev, resolution, lamp); 8035 8036 waitforpwm = FALSE; 8037 } */ 8038 } 8039 8040 } 8041 else 8042 rst = ERROR; 8043 8044 dev->status->warmup = FALSE; 8045 8046 DBG (DBG_FNC, "- Lamp_Warmup: %i\n", rst); 8047 8048 return rst; 8049} 8050 8051static SANE_Int 8052Scan_Start (struct st_device *dev) 8053{ 8054 SANE_Int rst; 8055 8056 DBG (DBG_FNC, "+ Scan_Start:\n"); 8057 8058 rst = ERROR; 8059 if (RTS_Enable_CCD (dev, dev->init_regs, 0x0f) == OK) 8060 { 8061 SANE_Byte Regs[RT_BUFFER_LEN], mlock; 8062 SANE_Int ypos, xpos, runb1; 8063 struct st_scanparams scancfg; 8064 struct st_hwdconfig hwdcfg; 8065 struct st_calibration myCalib; 8066 long tick; 8067 8068 memcpy (&Regs, dev->init_regs, RT_BUFFER_LEN * sizeof (SANE_Byte)); 8069 memcpy (&scancfg, &scan, sizeof (struct st_scanparams)); 8070 8071 dbg_ScanParams (&scancfg); 8072 8073 /* reserva buffer 6 dwords en fa84-fa9f */ 8074 memset (&hwdcfg, 0, sizeof (struct st_hwdconfig)); 8075 8076 /* wait till lamp is at home (should use timeout 8077 windows driver doesn't use it) 8078 */ 8079 tick = GetTickCount () + 10000; 8080 while ((Head_IsAtHome (dev, Regs) == FALSE) 8081 && (tick > GetTickCount ())); 8082 8083 if (v14b4 != 0) 8084 { 8085 SANE_Int lfaa0 = 0; 8086 8087 if (GainOffset_Counter_Inc (dev, &lfaa0) != OK) 8088 return 0x02; 8089 } 8090 8091 tick = GetTickCount (); 8092 8093 /* set margin references */ 8094 Refs_Set (dev, Regs, &scancfg); 8095 8096 /* locate head to right position */ 8097 Load_StripCoords (scantype, &ypos, &xpos); 8098 if (ypos != 0) 8099 Head_Relocate (dev, dev->motorcfg->parkhomemotormove, MTR_FORWARD, 8100 ypos); 8101 8102 /* perform lamp warmup */ 8103 if (Lamp_Warmup 8104 (dev, Regs, (scancfg.scantype == ST_NORMAL) ? FLB_LAMP : TMA_LAMP, 8105 scan.resolution_x) == ERROR) 8106 return ERROR; 8107 8108 /* Calibration process */ 8109 8110 /*592c */ 8111 if (Calib_CreateBuffers (dev, &myCalib, v14b4) != OK) 8112 return ERROR; 8113 8114 /*5947 */ 8115 8116/* 8117if (Calib_BlackShading_jkd(dev, Regs, &myCalib, &scancfg) == OK) 8118 Head_ParkHome(dev, TRUE, dev->motorcfg->parkhomemotormove); 8119*/ 8120 8121/* 8122if (Calib_test(dev, Regs, &myCalib, &scancfg) == OK ) 8123 Head_ParkHome(dev, TRUE, dev->motorcfg->parkhomemotormove); 8124*/ 8125 8126/* Calibrate White shading correction */ 8127 if ((RTS_Debug->wshading == TRUE) && (scan.scantype == ST_NORMAL)) 8128 if (WShading_Calibrate (dev, Regs, &myCalib, &scancfg) == OK) 8129 Head_ParkHome (dev, TRUE, dev->motorcfg->parkhomemotormove); 8130 8131 hwdcfg.calibrate = RTS_Debug->calibrate; 8132 8133 if (RTS_Debug->calibrate != 0) 8134 { 8135 /* Let's calibrate */ 8136 if ((scancfg.colormode != CM_COLOR) && (scancfg.channel == 3)) 8137 scancfg.colormode = CM_COLOR; 8138 8139 hwdcfg.arrangeline = 0; 8140 8141 if (scan.scantype == ST_NORMAL) 8142 { 8143 /* Calibration for reflective type */ 8144 8145 /*59e3 */ 8146 memcpy (&Regs, dev->init_regs, 8147 RT_BUFFER_LEN * sizeof (SANE_Byte)); 8148 8149 if (Calibration (dev, Regs, &scancfg, &myCalib, 0) != OK) 8150 { 8151 if (v14b4 == 0) 8152 Calib_FreeBuffers (&myCalib); 8153 return ERROR; 8154 } 8155 } 8156 else 8157 { 8158 /*59ed */ 8159 /* Calibration for negative/slide type */ 8160 8161 } 8162 8163 /*5af1 */ 8164 if (RTS_Debug->ScanWhiteBoard != FALSE) 8165 { 8166 Head_ParkHome (dev, TRUE, dev->motorcfg->basespeedmotormove); 8167 scan.ler = 1; 8168 } 8169 8170 scancfg.colormode = scan.colormode; 8171 } 8172 else 8173 { 8174 /*5b1e */ 8175 /*Don't calibrate */ 8176 if (scan.scantype == ST_NORMAL) 8177 { 8178 Lamp_Status_Set (dev, NULL, TRUE, FLB_LAMP); 8179 } 8180 else 8181 { 8182 if ((scan.scantype == ST_TA) || (scan.scantype == ST_NEG)) 8183 { 8184 /*SANE_Int ta_y_start; */ 8185 Lamp_Status_Set (dev, NULL, FALSE, TMA_LAMP); 8186 /*ta_y_start = 8187 get_value(SCAN_PARAM, TA_Y_START, 0x2508, usbfile); 8188 ta_y_start += (((((scan.coord.top * 3) * 5) * 5) * 32) / scancfg.resolution_x); 8189 if (ta_y_start >= 500) 8190 { 8191 Head_Relocate(dev, dev->motorcfg->highspeedmotormove, MTR_FORWARD, ta_y_start); 8192 scancfg.coord.top = 1; 8193 scan.ler = 1; 8194 } else 8195 { 8196 / *5ba9* / 8197 if (ta_y_start > 0) 8198 { 8199 Head_Relocate(dev, dev->motorcfg->basespeedmotormove, MTR_FORWARD, ta_y_start); 8200 scancfg.coord.top = 1; 8201 scan.ler = 1; 8202 } 8203 } */ 8204 } 8205 } 8206 } 8207 8208 /*5bd0 */ 8209 usleep (1000 * 200); 8210 8211 hwdcfg.scantype = scan.scantype; 8212 hwdcfg.motor_direction = MTR_FORWARD; 8213 8214 /* Set Origin */ 8215 if ((scan.scantype >= ST_NORMAL) || (scan.scantype <= ST_NEG)) 8216 { 8217 scancfg.coord.left += scan.ser; 8218 scancfg.coord.top += scan.ler; 8219 } 8220 8221 hwdcfg.sensorevenodddistance = dev->sensorcfg->evenodd_distance; 8222 hwdcfg.highresolution = (scancfg.resolution_x <= 1200) ? FALSE : TRUE; 8223 8224 /*5c55 */ 8225 /* 8226 if (RTS_Debug->calibrate == FALSE) 8227 { 8228 SANE_Int mytop = (((scancfg.coord.top * 5) * 5) * 16) / scancfg.resolution_y; 8229 if ((scancfg.resolution_y <= 150)&&(mytop < 300)) 8230 { 8231 scancfg.coord.top = scancfg.resolution_y / 4; 8232 } else 8233 { 8234 if (mytop < 100) 8235 scancfg.coord.top = scancfg.resolution_y / 12; 8236 } 8237 } 8238 */ 8239 8240 /*5cd9 */ 8241 if (compression != FALSE) 8242 hwdcfg.compression = TRUE; 8243 8244 /* setting arrangeline option */ 8245 hwdcfg.arrangeline = arrangeline; 8246 if (scancfg.resolution_x == 2400) 8247 { 8248 /* 5cfa */ 8249 if (scancfg.colormode != CM_COLOR) 8250 { 8251 if ((scancfg.colormode == CM_GRAY) && (scancfg.channel == 3)) 8252 hwdcfg.arrangeline = FIX_BY_SOFT; 8253 } 8254 else 8255 hwdcfg.arrangeline = FIX_BY_SOFT; 8256 } 8257 8258 /*5d12 */ 8259 if (dev->sensorcfg->type == CCD_SENSOR) 8260 { 8261 /*5d3a */ 8262 scancfg.coord.left += 24; 8263 switch (scancfg.resolution_x) 8264 { 8265 case 1200: 8266 scancfg.coord.left -= 63; 8267 break; 8268 case 2400: 8269 scancfg.coord.left -= 127; 8270 break; 8271 } 8272 } 8273 else 8274 { 8275 /*5d5a */ 8276 /* CIS sensor */ 8277 /*5d6d */ 8278 scancfg.coord.left += 50; 8279 switch (scancfg.resolution_x) 8280 { 8281 case 1200: 8282 scancfg.coord.left -= 63; 8283 break; 8284 case 2400: 8285 scancfg.coord.left -= 127; 8286 break; 8287 } 8288 } 8289 8290 /* 5d92 */ 8291 DBG (DBG_FNC, " ->Scan_Start xStart=%i, xExtent=%i\n", 8292 scancfg.coord.left, scancfg.coord.width); 8293 8294 runb1 = 1; 8295 if (scan.scantype == ST_NORMAL) 8296 { 8297 /*5db7 */ 8298 if ((scancfg.resolution_x == 1200) 8299 || (scancfg.resolution_x == 2400)) 8300 { 8301 /*5e41 */ 8302 if ((scancfg.resolution_y / 10) > scancfg.coord.top) 8303 runb1 = 0; 8304 } 8305 else 8306 { 8307 if ((scancfg.resolution_x == 600) 8308 && (RTS_Debug->usbtype == USB11) 8309 && (scancfg.colormode == CM_COLOR)) 8310 { 8311 /*5ded */ 8312 if ((scancfg.resolution_y / 10) > scancfg.coord.top) 8313 runb1 = 0; 8314 } 8315 else 8316 { 8317 if ((scancfg.resolution_x == 600) 8318 || (scancfg.resolution_x == 300)) 8319 { 8320 /*5e11 */ 8321 if (scancfg.resolution_y > scancfg.coord.top) 8322 runb1 = 0; 8323 } 8324 else 8325 runb1 = 0; 8326 } 8327 } 8328 } 8329 else 8330 { 8331 /*5e7c *//* entra aquí */ 8332 if ((scancfg.resolution_y / 10) > scancfg.coord.top) 8333 runb1 = 0; 8334 } 8335 /*5eb1 */ 8336 if (runb1 == 1) /*entra */ 8337 { 8338 SANE_Int val1 = scancfg.coord.top - (scancfg.resolution_y / 10); 8339 scancfg.coord.top -= val1; 8340 Head_Relocate (dev, dev->motorcfg->highspeedmotormove, MTR_FORWARD, (dev->motorcfg->resolution / scancfg.resolution_y) * val1); /*x168 */ 8341 } 8342 8343 /*5efe */ 8344 if (RTS_Debug->calibrate != FALSE) 8345 { 8346 if (use_gamma_tables != FALSE) 8347 { 8348 hwdcfg.use_gamma_tables = TRUE; 8349 hp_gamma->depth = 0; 8350 } 8351 8352 /*5f24 */ 8353 hwdcfg.white_shading = TRUE; 8354 hwdcfg.black_shading = TRUE; 8355 hwdcfg.unk3 = 0; 8356 RTS_Setup (dev, Regs, &scancfg, &hwdcfg, &calibdata->gain_offset); 8357 8358 myCalib.shading_type = 0; 8359 myCalib.shadinglength = 8360 min (myCalib.shadinglength, scan.shadinglength); 8361 8362 if (scancfg.colormode != CM_COLOR) 8363 { 8364 if ((scancfg.channel > 0) && (scancfg.channel < 3)) 8365 myCalib.WRef[0] = myCalib.WRef[scancfg.channel]; 8366 } 8367 8368 RTS_WriteRegs (dev->usb_handle, Regs); 8369 8370 /* apply gamma if required */ 8371 Gamma_Apply (dev, Regs, &scancfg, &hwdcfg, hp_gamma); 8372 8373 Shading_apply (dev, Regs, &scancfg, &myCalib); 8374 8375 /* Save to file? */ 8376 if (RTS_Debug->DumpShadingData != FALSE) 8377 dump_shading (&myCalib); /*5ff9 */ 8378 } 8379 else 8380 RTS_Setup (dev, Regs, &scancfg, &hwdcfg, default_gain_offset); 8381 8382 /*602a */ 8383 RTS_Debug->calibrate = hwdcfg.calibrate; 8384 binarythresholdh = bw_threshold; 8385 binarythresholdl = bw_threshold; 8386 DBG (DBG_FNC, "> bw threshold -- hi=%i, lo=%i\n", binarythresholdh, 8387 binarythresholdl); 8388 8389 /* set threshold high */ 8390 data_lsb_set (&Regs[0x1a0], binarythresholdh, 2); 8391 8392 /* set threshold low */ 8393 data_lsb_set (&Regs[0x19e], binarythresholdl, 2); 8394 8395 /* if has motorcurves... */ 8396 if ((Regs[0xdf] & 0x10) != 0) 8397 data_bitset (&Regs[0x01], 0x02, 1); 8398 8399 /* Set MLOCK */ 8400 mlock = get_value (SCAN_PARAM, MLOCK, 0, usbfile) & 1; 8401 data_bitset (&Regs[0x00], 0x10, mlock); /*---x----*/ 8402 8403 if (dev->motorcfg->changemotorcurrent != FALSE) 8404 Motor_Change (dev, Regs, 8405 Motor_GetFromResolution (scancfg.resolution_x)); 8406 8407 /* set gain control mode */ 8408 Lamp_SetGainMode (dev, Regs, scancfg.resolution_x, 8409 Lamp_GetGainMode (dev, scancfg.resolution_x, 8410 scan.scantype)); 8411 8412 RTS_WaitScanEnd (dev, 15000); 8413 if (v14b4 == 0) 8414 Calib_FreeBuffers (&myCalib); 8415 8416 /* release motor */ 8417 Motor_Release (dev); 8418 8419 8420#ifdef developing 8421/* prueba(Regs); 8422 dbg_registers(Regs);*/ 8423 /*WShading_Calibrate(dev, Regs, &myCalib, &scancfg); */ 8424 /*shadingtest1(dev, Regs, &myCalib); */ 8425#endif 8426 8427 if (RTS_Warm_Reset (dev) == OK) 8428 { 8429 RTS_WriteRegs (dev->usb_handle, Regs); 8430 usleep (1000 * 500); 8431 8432 if (RTS_Execute (dev) == OK) 8433 { 8434 Lamp_Status_Timer_Set (dev, 0); 8435 8436 /* Let scanner some time to store some data */ 8437 if ((dev->chipset->model == RTS8822L_02A) 8438 && (scancfg.resolution_x > 2400)) 8439 usleep (1000 * 5000); 8440 8441 rst = OK; 8442 } 8443 } 8444 } 8445 8446 DBG (DBG_FNC, "- Scan_Start: %i\n", rst); 8447 8448 return rst; 8449} 8450 8451static SANE_Int 8452RTS_Setup_Motor (struct st_device *dev, SANE_Byte * Regs, 8453 struct st_scanparams *scancfg, SANE_Int somevalue) 8454{ 8455 SANE_Int rst = ERROR; /* default */ 8456 8457 DBG (DBG_FNC, "+ RTS_Setup_Motor(*Regs, *scancfg, somevalue=%i):\n", 8458 somevalue); 8459 dbg_ScanParams (scancfg); 8460 8461 if ((Regs != NULL) && (scancfg != NULL)) 8462 { 8463 SANE_Int colormode, mymode; 8464 8465 colormode = ((scancfg->colormode != CM_COLOR) 8466 && (scancfg->channel == 3)) ? 3 : scancfg->colormode; 8467 mymode = 8468 RTS_GetScanmode (dev, scantype, colormode, scancfg->resolution_x); 8469 8470 if (mymode != -1) 8471 { 8472 SANE_Int mbs[2] = { 0 }; /* motor back steps */ 8473 SANE_Int step_size, step_type, dummyline, myvalue, lf02c; 8474 struct st_scanmode *sm; 8475 8476 sm = dev->scanmodes[mymode]; 8477 8478 /* set motor step type */ 8479 data_bitset (&Regs[0xd9], 0x70, sm->scanmotorsteptype); /*-xxx----*/ 8480 8481 /* set motor direction (polarity) */ 8482 data_bitset (&Regs[0xd9], 0x80, somevalue >> 3); /*e------- */ 8483 8484 /* next value doesn't seem to have any effect */ 8485 data_bitset (&Regs[0xd9], 0x0f, somevalue); /*----efgh*/ 8486 8487 /* 0 enable/1 disable motor */ 8488 data_bitset (&Regs[0xdd], 0x80, somevalue >> 4); /*d------- */ 8489 8490 /* next value doesn't seem to have any effect */ 8491 data_bitset (&Regs[0xdd], 0x40, somevalue >> 4); /*-d------*/ 8492 8493 switch (sm->scanmotorsteptype) 8494 { 8495 case STT_OCT: 8496 step_type = 8; 8497 break; 8498 case STT_QUART: 8499 step_type = 4; 8500 break; 8501 case STT_HALF: 8502 step_type = 2; 8503 break; 8504 default: 8505 step_type = 1; 8506 break; /* STT_FULL */ 8507 } 8508 8509 /* set dummy lines */ 8510 dummyline = sm->dummyline; 8511 if (dummyline == 0) 8512 dummyline++; 8513 8514 data_bitset (&Regs[0xd6], 0xf0, dummyline); /*xxxx---- */ 8515 8516 /* Set if motor has curves */ 8517 data_bitset (&Regs[0xdf], 0x10, ((sm->motorcurve != -1) ? 1 : 0)); /*---x----*/ 8518 8519 /* set last step of deccurve.scanbufferfull table to 16 */ 8520 data_lsb_set (&Regs[0xea], 0x10, 3); 8521 8522 /* set last step of deccurve.normalscan table to 16 */ 8523 data_lsb_set (&Regs[0xed], 0x10, 3); 8524 8525 /* set last step of deccurve.smearing table to 16 */ 8526 data_lsb_set (&Regs[0xf0], 0x10, 3); 8527 8528 /* set last step of deccurve.parkhome table to 16 */ 8529 data_lsb_set (&Regs[0xf3], 0x10, 3); 8530 8531 /* set step size */ 8532 step_size = 8533 _B0 ((dev->motorcfg->resolution * step_type) / 8534 (dummyline * scancfg->resolution_y)); 8535 data_lsb_set (&Regs[0xe0], step_size - 1, 1); 8536 8537 /* set line exposure time */ 8538 myvalue = data_lsb_get (&Regs[0x30], 3); 8539 myvalue += ((myvalue + 1) % step_size); 8540 data_lsb_set (&Regs[0x30], myvalue, 3); 8541 8542 /* set last step of accurve.normalscan table */ 8543 myvalue = ((myvalue + 1) / step_size) - 1; 8544 data_lsb_set (&Regs[0xe1], myvalue, 3); 8545 8546 /* 42b30eb */ 8547 lf02c = 0; 8548 if (sm->motorcurve != -1) 8549 { 8550 if (sm->motorcurve < dev->mtrsetting_count) 8551 { 8552 struct st_motorcurve *ms = dev->mtrsetting[sm->motorcurve]; 8553 ms->motorbackstep = sm->motorbackstep; 8554 } 8555 8556 DBG (DBG_FNC, " -> Setting up step motor using motorcurve %i\n", 8557 sm->motorcurve); 8558 lf02c = Motor_Setup_Steps (dev, Regs, sm->motorcurve); 8559 8560 /* set motor back steps */ 8561 mbs[1] = sm->motorbackstep; 8562 if (mbs[1] >= (smeardeccurvecount + smearacccurvecount)) 8563 mbs[0] = 8564 mbs[1] - (smeardeccurvecount + smearacccurvecount) + 2; 8565 else 8566 mbs[0] = 0; 8567 8568 if (mbs[1] >= (deccurvecount + acccurvecount)) 8569 mbs[1] -= (deccurvecount + acccurvecount) + 2; 8570 else 8571 mbs[1] = 0; 8572 } 8573 else 8574 { 8575 /* this scanner hasn't got any motorcurve */ 8576 8577 /* set last step of accurve.smearing table (same as accurve.normalscan) */ 8578 data_lsb_set (&Regs[0xe4], myvalue, 3); 8579 8580 /* set last step of accurve.parkhome table (same as accurve.normalscan) */ 8581 data_lsb_set (&Regs[0xe7], myvalue, 3); 8582 8583 /* both motorbacksteps are equal */ 8584 mbs[0] = sm->motorbackstep; 8585 mbs[1] = sm->motorbackstep; 8586 } 8587 8588 /* show msi and motorbacksteps */ 8589 DBG (DBG_FNC, " -> msi = %i\n", sm->msi); 8590 DBG (DBG_FNC, " -> motorbackstep1 = %i\n", mbs[0]); 8591 DBG (DBG_FNC, " -> motorbackstep2 = %i\n", mbs[1]); 8592 8593 /* set msi */ 8594 data_bitset (&Regs[0xda], 0xff, _B0 (sm->msi)); /*xxxxxxxx */ 8595 data_bitset (&Regs[0xdd], 0x03, _B1 (sm->msi)); /*------xx*/ 8596 8597 /* set motorbackstep (a) */ 8598 data_bitset (&Regs[0xdb], 0xff, _B0 (mbs[0])); /*xxxxxxxx */ 8599 data_bitset (&Regs[0xdd], 0x0c, _B1 (mbs[0])); /*----xx--*/ 8600 8601 /* set motorbackstep (b) */ 8602 data_bitset (&Regs[0xdc], 0xff, _B0 (mbs[1])); /*xxxxxxxx */ 8603 data_bitset (&Regs[0xdd], 0x30, _B1 (mbs[1])); /*--xx----*/ 8604 8605 /* 328b */ 8606 8607 /* get dummy lines count */ 8608 dummyline = data_bitget (&Regs[0xd6], 0xf0); 8609 8610 myvalue = scancfg->coord.top * (dummyline * step_size); 8611 8612 if (lf02c >= myvalue) 8613 scancfg->coord.top = 1; 8614 else 8615 scancfg->coord.top -= (lf02c / (dummyline * step_size)) - 1; 8616 8617 rst = lf02c; /* Result from Motor_Setup_Steps */ 8618 } 8619 } 8620 8621 DBG (DBG_FNC, "- RTS_Setup_Motor: %i\n", rst); 8622 8623 return rst; 8624} 8625 8626static void 8627RTS_Setup_Exposure_Times (SANE_Byte * Regs, struct st_scanparams *scancfg, 8628 struct st_scanmode *sm) 8629{ 8630 DBG (DBG_FNC, "> RTS_Setup_Exposure_Times\n"); 8631 8632 if ((sm != NULL) && (Regs != NULL) && (scancfg != NULL)) 8633 { 8634 SANE_Int myexpt[3], linexpt, a; 8635 8636 /* calculate line exposure time */ 8637 linexpt = sm->ctpc + 1; 8638 if (RTS_Debug->usbtype == USB11) 8639 linexpt *= sm->multiexposureforfullspeed; 8640 8641 if (scancfg->depth > 8) 8642 linexpt *= sm->multiexposurefor16bitmode; 8643 8644 linexpt--; 8645 8646 /* generate exposure times for each channel color */ 8647 for (a = CL_RED; a <= CL_BLUE; a++) 8648 { 8649 if ((linexpt > sm->mexpt[a]) && (sm->expt[a] == 0)) 8650 sm->expt[a] = sm->mexpt[a]; 8651 8652 myexpt[a] = (sm->expt[a] == 0) ? sm->mexpt[a] : sm->expt[a]; 8653 } 8654 8655 /* save exposure times */ 8656 DBG (DBG_FNC, "-> Exposure times : %04x, %04x, %04x\n", sm->expt[0], 8657 sm->expt[1], sm->expt[2]); 8658 data_lsb_set (&Regs[0x36], sm->expt[CL_RED], 3); 8659 data_lsb_set (&Regs[0x3c], sm->expt[CL_GREEN], 3); 8660 data_lsb_set (&Regs[0x42], sm->expt[CL_BLUE], 3); 8661 8662 /* save maximum exposure times */ 8663 DBG (DBG_FNC, "-> Maximum exposure times: %04x, %04x, %04x\n", 8664 sm->mexpt[0], sm->mexpt[1], sm->mexpt[2]); 8665 data_lsb_set (&Regs[0x33], sm->mexpt[CL_RED], 3); 8666 data_lsb_set (&Regs[0x39], sm->mexpt[CL_GREEN], 3); 8667 data_lsb_set (&Regs[0x3f], sm->mexpt[CL_BLUE], 3); 8668 8669 /* save line exposure time */ 8670 data_lsb_set (&Regs[0x30], linexpt, 3); 8671 8672 /* scancfg->expt = lowest value */ 8673 scancfg->expt = min (min (myexpt[1], myexpt[2]), myexpt[0]); 8674 } 8675} 8676 8677static SANE_Int 8678RTS_Setup_Line_Distances (struct st_device *dev, SANE_Byte * Regs, 8679 struct st_scanparams *scancfg, 8680 struct st_hwdconfig *hwdcfg, SANE_Int mycolormode, 8681 SANE_Int arrangeline) 8682{ 8683 SANE_Int iLineDistance = 0; 8684 8685 if (arrangeline == FIX_BY_HARD) 8686 { 8687 /* we don't need to arrange retrieved line */ 8688 SANE_Int mylinedistance, myevenodddist; 8689 8690 mylinedistance = 8691 (dev->sensorcfg->line_distance * scancfg->resolution_y) / 8692 dev->sensorcfg->resolution; 8693 8694 if (hwdcfg->highresolution == TRUE) 8695 myevenodddist = 8696 (hwdcfg->sensorevenodddistance * scancfg->resolution_y) / 8697 dev->sensorcfg->resolution; 8698 else 8699 myevenodddist = 0; 8700 8701 data_bitset (&Regs[0x149], 0x3f, myevenodddist); 8702 data_bitset (&Regs[0x14a], 0x3f, mylinedistance); 8703 data_bitset (&Regs[0x14b], 0x3f, mylinedistance + myevenodddist); 8704 data_bitset (&Regs[0x14c], 0x3f, mylinedistance * 2); 8705 data_bitset (&Regs[0x14d], 0x3f, (mylinedistance * 2) + myevenodddist); 8706 } 8707 else 8708 { 8709 /* arrange retrieved line */ 8710 data_bitset (&Regs[0x149], 0x3f, 0); 8711 data_bitset (&Regs[0x14a], 0x3f, 0); 8712 data_bitset (&Regs[0x14b], 0x3f, 0); 8713 data_bitset (&Regs[0x14c], 0x3f, 0); 8714 data_bitset (&Regs[0x14d], 0x3f, 0); 8715 8716 if (arrangeline == FIX_BY_SOFT) 8717 { 8718 if (hwdcfg->highresolution == FALSE) 8719 { 8720 if (mycolormode == CM_COLOR) 8721 { 8722 iLineDistance = 8723 (dev->sensorcfg->line_distance * scan2.resolution_y) * 2; 8724 iLineDistance = 8725 (iLineDistance / dev->sensorcfg->resolution) + 1; 8726 if (iLineDistance < 2) 8727 iLineDistance = 2; 8728 } 8729 } 8730 else 8731 { 8732 /* bcc */ 8733 if (mycolormode == CM_COLOR) 8734 iLineDistance = 8735 ((dev->sensorcfg->line_distance * 2) + 8736 hwdcfg->sensorevenodddistance) * scan2.resolution_y; 8737 else 8738 iLineDistance = 8739 dev->sensorcfg->line_distance * scan2.resolution_y; 8740 8741 iLineDistance = 8742 (iLineDistance / dev->sensorcfg->resolution) + 1; 8743 if (iLineDistance < 2) 8744 iLineDistance = 2; 8745 } 8746 8747 /* c25 */ 8748 iLineDistance &= 0xffff; 8749 v15b4 = (iLineDistance > 0) ? 1 : 0; 8750 imagesize += iLineDistance * bytesperline; 8751 } 8752 } 8753 8754 DBG (DBG_FNC, 8755 "> RTS_Setup_Line_Distances(*Regs, *scancfg, *hwdcfg, mycolormode=%i, arrangeline=%i): %i\n", 8756 mycolormode, arrangeline, iLineDistance); 8757 8758 return iLineDistance; 8759} 8760 8761static SANE_Int 8762RTS_Setup_Depth (SANE_Byte * Regs, struct st_scanparams *scancfg, 8763 SANE_Int mycolormode) 8764{ 8765 /* channels_per_line = channels_per_dot * scan.width 8766 bytes_per_line = channels_per_line * bits_per_channel 8767 */ 8768 8769 SANE_Int bytes_per_line = 0; 8770 8771 if ((scancfg != NULL) && (Regs != NULL)) 8772 { 8773 SANE_Int channels_per_line = 8774 data_bitget (&Regs[0x12], 0xc0) * scancfg->coord.width; 8775 8776 bytes_per_line = channels_per_line; 8777 8778 /* set bits per channel in shading correction's register (0x1cf) */ 8779 if (mycolormode == CM_LINEART) 8780 { 8781 /* lineart mode */ 8782 bytes_per_line = (bytes_per_line + 7) / 8; 8783 data_bitset (&Regs[0x1cf], 0x30, 3); /*--11----*/ 8784 } 8785 else 8786 { 8787 /*f0c */ 8788 switch (scancfg->depth) 8789 { 8790 case 16: 8791 /* 16 bits per channel */ 8792 bytes_per_line *= 2; 8793 data_bitset (&Regs[0x1cf], 0x30, 2); /*--10----*/ 8794 break; 8795 case 12: 8796 /* 12 bits per channel */ 8797 bytes_per_line *= 2; 8798 data_bitset (&Regs[0x1cf], 0x30, 1); /*--01----*/ 8799 break; 8800 default: 8801 /* 8 bits per channel */ 8802 data_bitset (&Regs[0x1cf], 0x30, 0); /*--00----*/ 8803 break; 8804 } 8805 } 8806 } 8807 8808 return bytes_per_line; 8809} 8810 8811static void 8812RTS_Setup_Shading (SANE_Byte * Regs, struct st_scanparams *scancfg, 8813 struct st_hwdconfig *hwdcfg, SANE_Int bytes_per_line) 8814{ 8815 DBG (DBG_FNC, 8816 "> RTS_Setup_Shading(*Regs, *scancfg, *hwdcfg, bytes_per_line=%i)\n", 8817 bytes_per_line); 8818 8819 if ((Regs != NULL) && (hwdcfg != NULL)) 8820 { 8821 SANE_Int dots_count, myvalue, myvalue2, mem_available, resolution_ratio, 8822 sensor_line_distance; 8823 SANE_Int channels, table_size; 8824 8825 resolution_ratio = Regs[0x0c0] & 0x1f; 8826 8827 /* 50de */ 8828 data_bitset (&Regs[0x1bf], 0x18, hwdcfg->unk3); /*---xx---*/ 8829 8830 /* Enable black shading correction ? */ 8831 data_bitset (&Regs[0x1cf], 0x08, hwdcfg->black_shading); /*----x---*/ 8832 8833 /* Enable white shading correction ? */ 8834 data_bitset (&Regs[0x1cf], 0x04, hwdcfg->white_shading); /*-----x--*/ 8835 8836 if ((hwdcfg->white_shading != FALSE) && (hwdcfg->black_shading != FALSE) 8837 && (hwdcfg->unk3 != 0)) 8838 data_bitset (&Regs[0x1cf], 0x04, 0); /*-----x--*/ 8839 8840 table_size = 0; 8841 8842 /* if hwdcfg->black_shading */ 8843 if ((Regs[0x1cf] & 8) != 0) 8844 table_size = (resolution_ratio * scancfg->coord.width) * 2; /* black shading buffer size? */ 8845 8846 /* if hwdcfg->white_shading */ 8847 if ((Regs[0x1cf] & 4) != 0) 8848 table_size += (resolution_ratio * scancfg->coord.width) * 2; /* white shading buffer size? */ 8849 8850 /* Regs 0x1ba, 0x1bb, 0x1bd, 0x1c0 seem to be 4 pointers 8851 to some buffer related to shading correction */ 8852 8853 Regs[0x1ba] = 0x00; 8854 table_size = (table_size + v160c_block_size - 1) / v160c_block_size; 8855 table_size = ((table_size + 15) / 16) + 16; 8856 8857 Regs[0x1bf] &= 0xfe; 8858 Regs[0x1bb] = _B0 (table_size); 8859 Regs[0x1bc] = _B1 (table_size); 8860 Regs[0x1bf] |= _B2 (table_size) & 1; /*-------x*/ 8861 8862 Regs[0x1bf] &= 0xf9; 8863 Regs[0x1bd] = _B0 (table_size * 2); 8864 Regs[0x1be] = _B1 (table_size * 2); 8865 Regs[0x1bf] |= (_B2 (table_size * 2) & 3) << 1; /*-----xx-*/ 8866 8867 data_wide_bitset (&Regs[0x1c0], 0xfffff, table_size * 3); 8868 8869 mem_available = mem_total - ((table_size * 3) * 16); 8870 sensor_line_distance = Regs[0x14a] & 0x3f; 8871 8872 /* select case channels_per_dot */ 8873 channels = data_lsb_get (&Regs[0x12], 1) >> 6; 8874 8875 switch (channels) 8876 { 8877 case 3: /* 3 channels per dot */ 8878 /* 528d */ 8879 dots_count = bytes_per_line / 3; /* 882 */ 8880 myvalue = 8881 (((sensor_line_distance + 1) * dots_count) + v160c_block_size - 8882 1) / v160c_block_size; 8883 myvalue2 = myvalue; 8884 mem_available = (mem_available - (myvalue * 3) + 2) / 3; 8885 8886 myvalue += (table_size * 3) * 8; 8887 myvalue = ((myvalue * 2) + mem_available); 8888 8889 data_bitset (&Regs[0x1c2], 0xf0, _B2 ((myvalue / 16) + 1)); /* 4 higher bits xxxx---- */ 8890 data_wide_bitset (&Regs[0x1c3], 0xffff, (myvalue / 16) + 1); /* 16 lower bits */ 8891 8892 myvalue = myvalue + myvalue2 + mem_available; 8893 data_wide_bitset (&Regs[0x1c5], 0xfffff, (myvalue / 16) + 1); 8894 break; 8895 case 2: /* 2 channels per dot */ 8896 dots_count = bytes_per_line / 2; 8897 myvalue = 8898 (((sensor_line_distance + 1) * dots_count) + v160c_block_size - 8899 1) / v160c_block_size; 8900 mem_available = ((mem_available - myvalue) + 1) / 2; 8901 myvalue += (((table_size * 3) + mem_available) / 16) + 1; 8902 8903 data_bitset (&Regs[0x1c2], 0xf0, _B2 (myvalue)); /* 4 higher bits xxxx---- */ 8904 data_wide_bitset (&Regs[0x1c3], 0xffff, myvalue); /* 16 lower bits */ 8905 break; 8906 default: 8907 dots_count = bytes_per_line; 8908 break; 8909 } 8910 8911 Regs[0x01c7] &= 0x0f; 8912 Regs[0x01c8] = _B0 ((mem_total - 1) / 16); 8913 Regs[0x01c9] = _B1 ((mem_total - 1) / 16); 8914 Regs[0x01c7] |= (_B2 ((mem_total - 1) / 16) & 0x0f) << 4; 8915 8916 mem_available -= (dots_count + v160c_block_size - 1) / v160c_block_size; 8917 mem_available /= 16; 8918 Regs[0x0712] &= 0x0f; 8919 Regs[0x0710] = _B0 (mem_available); 8920 Regs[0x0711] = _B1 (mem_available); 8921 Regs[0x0712] |= _B0 (_B2 (mem_available) << 4); /*xxxx---- */ 8922 8923 Regs[0x0713] = 0x00; 8924 Regs[0x0714] = 0x10; 8925 Regs[0x0715] &= 0xf0; 8926 } 8927} 8928 8929static void 8930RTS_Setup_Arrangeline (struct st_device *dev, struct st_hwdconfig *hwdcfg, 8931 SANE_Int colormode) 8932{ 8933 dev->scanning->arrange_compression = 8934 (colormode == CM_LINEART) ? FALSE : hwdcfg->compression; 8935 8936 if ((colormode == CM_LINEART) 8937 || ((colormode == CM_GRAY) && (hwdcfg->highresolution == FALSE))) 8938 arrangeline2 = 0; 8939 else 8940 arrangeline2 = hwdcfg->arrangeline; 8941 8942 dev->scanning->arrange_hres = hwdcfg->highresolution; 8943 dev->scanning->arrange_sensor_evenodd_dist = 8944 (hwdcfg->highresolution == FALSE) ? 0 : hwdcfg->sensorevenodddistance; 8945} 8946 8947static void 8948RTS_Setup_Channels (struct st_device *dev, SANE_Byte * Regs, 8949 struct st_scanparams *scancfg, SANE_Int mycolormode) 8950{ 8951 DBG (DBG_FNC, "> RTS_Setup_Channels(colormode=%i)\n", mycolormode); 8952 8953 if ((scancfg != NULL) && (Regs != NULL)) 8954 { 8955 if ((mycolormode != CM_COLOR) && (mycolormode != 3)) 8956 { 8957 /* CM_GRAY || CM_LINEART */ 8958 if (scancfg->samplerate == LINE_RATE) 8959 { 8960 /* Setting channels_per_dot to 1 */ 8961 data_bitset (&Regs[0x12], 0xc0, 1); /*01------ */ 8962 8963 /* setting one rgb_channel_order */ 8964 data_bitset (&Regs[0x12], 0x03, dev->sensorcfg->rgb_order[scancfg->channel]); /*------xx*/ 8965 8966 /* set sensor_channel_color_order */ 8967 data_bitset (&Regs[0x60a], 0x3f, 6); /*--xxxxxx*/ 8968 8969 /* set samplerate */ 8970 data_bitset (&Regs[0x1cf], 0x40, PIXEL_RATE); /*-x------*/ 8971 8972 /* set unknown data */ 8973 data_bitset (&Regs[0x1cf], 0x80, 1); /*x------- */ 8974 8975 if (scancfg->channel == dev->sensorcfg->rgb_order[1]) 8976 { 8977 /* mexpts[CL_RED] = mexpts[CL_GREEN] */ 8978 data_lsb_set (&Regs[0x33], data_lsb_get (&Regs[0x39], 3), 8979 3); 8980 8981 /* expts[CL_RED] = expts[CL_GREEN] */ 8982 data_lsb_set (&Regs[0x36], data_lsb_get (&Regs[0x3c], 3), 8983 3); 8984 } 8985 else if (scancfg->channel == dev->sensorcfg->rgb_order[2]) 8986 { 8987 /* mexpts[CL_RED] = mexpts[CL_BLUE] */ 8988 data_lsb_set (&Regs[0x33], data_lsb_get (&Regs[0x3f], 3), 8989 3); 8990 8991 /* expts[CL_RED] = expts[CL_BLUE] */ 8992 data_lsb_set (&Regs[0x36], data_lsb_get (&Regs[0x42], 3), 8993 3); 8994 } 8995 } 8996 else 8997 { 8998 /* e01 */ 8999 /* setting channels_per_dot to 2 */ 9000 data_bitset (&Regs[0x12], 0xc0, 2); 9001 9002 /* set two channel color order */ 9003 data_bitset (&Regs[0x12], 0x03, dev->sensorcfg->channel_gray[0]); /*------xx*/ 9004 data_bitset (&Regs[0x12], 0x0c, dev->sensorcfg->channel_gray[1]); /*----xx--*/ 9005 9006 /* set samplerate */ 9007 data_bitset (&Regs[0x1cf], 0x40, LINE_RATE); 9008 9009 /* set unknown data */ 9010 data_bitset (&Regs[0x1cf], 0x80, 1); 9011 } 9012 } 9013 else 9014 { 9015 /* CM_COLOR || 3 */ 9016 /* e42 */ 9017 9018 /* setting channels_per_dot to 3 */ 9019 data_bitset (&Regs[0x12], 0xc0, 3); 9020 9021 /* setting samplerate */ 9022 data_bitset (&Regs[0x1cf], 0x40, scancfg->samplerate); 9023 9024 /* set unknown data */ 9025 data_bitset (&Regs[0x1cf], 0x80, 0); 9026 9027 /* set sensor chanel_color_order */ 9028 data_bitset (&Regs[0x60a], 0x03, dev->sensorcfg->channel_color[2]); /*------xx*/ 9029 data_bitset (&Regs[0x60a], 0x0c, dev->sensorcfg->channel_color[1]); /*----xx--*/ 9030 data_bitset (&Regs[0x60a], 0x30, dev->sensorcfg->channel_color[0]); /*--xx----*/ 9031 9032 /* set rgb_channel_order */ 9033 data_bitset (&Regs[0x12], 0x03, dev->sensorcfg->rgb_order[0]); /*------xx*/ 9034 data_bitset (&Regs[0x12], 0x0c, dev->sensorcfg->rgb_order[1]); /*----xx--*/ 9035 data_bitset (&Regs[0x12], 0x30, dev->sensorcfg->rgb_order[2]); /*--xx----*/ 9036 } 9037 } 9038} 9039 9040static SANE_Int 9041RTS_Setup (struct st_device *dev, SANE_Byte * Regs, 9042 struct st_scanparams *scancfg, struct st_hwdconfig *hwdcfg, 9043 struct st_gain_offset *gain_offset) 9044{ 9045 SANE_Int rst = ERROR; /* default */ 9046 SANE_Int lSMode; 9047 SANE_Byte mycolormode; 9048 9049 DBG (DBG_FNC, "+ RTS_Setup:\n"); 9050 dbg_ScanParams (scancfg); 9051 dbg_hwdcfg (hwdcfg); 9052 9053 mycolormode = scancfg->colormode; 9054 if (scancfg->colormode != CM_COLOR) 9055 { 9056 if (scancfg->colormode == CM_LINEART) 9057 scancfg->depth = 8; 9058 9059 if (scancfg->channel == 3) 9060 { 9061 if (scancfg->colormode == CM_GRAY) 9062 mycolormode = (hwdcfg->arrangeline != FIX_BY_SOFT) ? 3 : CM_COLOR; 9063 else 9064 mycolormode = 3; 9065 } 9066 } 9067 9068 /* 42b47d6 */ 9069 memcpy (&scan2, scancfg, sizeof (struct st_scanparams)); 9070 9071 scantype = hwdcfg->scantype; 9072 lSMode = 9073 RTS_GetScanmode (dev, scantype, mycolormode, scancfg->resolution_x); 9074 if (lSMode >= 0) 9075 { 9076 struct st_scanmode *sm = dev->scanmodes[lSMode]; 9077 9078 if (sm != NULL) 9079 { 9080 SANE_Int dummyline, iLineDistance, resolution_ratio, bytes_per_line; 9081 struct st_coords rts_coords; 9082 9083 iLineDistance = 0; 9084 9085 scancfg->timing = sm->timing; 9086 scancfg->sensorresolution = 9087 dev->timings[scancfg->timing]->sensorresolution; 9088 scancfg->shadinglength = 9089 (((scancfg->sensorresolution * 17) / 2) + 3) & 0xfffffffc; 9090 scancfg->samplerate = sm->samplerate; 9091 9092 hwdcfg->motorplus = sm->motorplus; 9093 9094 /* set systemclock */ 9095 data_bitset (&Regs[0x00], 0x0f, sm->systemclock); 9096 9097 /* setting exposure times */ 9098 RTS_Setup_Exposure_Times (Regs, scancfg, sm); 9099 9100 /* setting arranges */ 9101 RTS_Setup_Arrangeline (dev, hwdcfg, mycolormode); 9102 9103 /* set up line distances */ 9104 iLineDistance = 9105 RTS_Setup_Line_Distances (dev, Regs, scancfg, hwdcfg, mycolormode, 9106 arrangeline); 9107 9108 /* 4c67 */ 9109 9110 /* setup channel colors */ 9111 RTS_Setup_Channels (dev, Regs, scancfg, mycolormode); 9112 9113 /* setup depth */ 9114 bytes_per_line = RTS_Setup_Depth (Regs, scancfg, mycolormode); 9115 9116 /* f61 */ 9117 9118 /* Set resolution ratio */ 9119 resolution_ratio = 9120 (scancfg->sensorresolution / scancfg->resolution_x) & 0x1f; 9121 data_bitset (&Regs[0xc0], 0x1f, resolution_ratio); 9122 9123 /* set sensor timing values */ 9124 RTS_Setup_SensorTiming (dev, scancfg->timing, Regs); 9125 9126 data_bitset (&Regs[0xd8], 0x40, ((scantype == ST_NORMAL) ? 0 : 1)); /*-x------*/ 9127 9128 /* Use static head ? */ 9129 data_bitset (&Regs[0xd8], 0x80, ((hwdcfg->static_head == FALSE) ? 1 : 0)); /*x------- */ 9130 9131 /* Setting up gamma */ 9132 RTS_Setup_Gamma (Regs, hwdcfg); 9133 9134 /* setup shading correction */ 9135 RTS_Setup_Shading (Regs, scancfg, hwdcfg, bytes_per_line); 9136 9137 /* setup stepper motor */ 9138 hwdcfg->startpos = 9139 RTS_Setup_Motor (dev, Regs, scancfg, 9140 hwdcfg->motor_direction | MTR_ENABLED); 9141 9142 /* set coordinates */ 9143 dummyline = data_bitget (&Regs[0xd6], 0xf0); 9144 9145 if (scancfg->coord.left == 0) 9146 scancfg->coord.left++; 9147 if (scancfg->coord.top == 0) 9148 scancfg->coord.top++; 9149 9150 rts_coords.left = scancfg->coord.left * resolution_ratio; 9151 rts_coords.width = scancfg->coord.width * resolution_ratio; 9152 rts_coords.top = scancfg->coord.top * dummyline; 9153 rts_coords.height = 9154 ((Regs[0x14d] & 0x3f) + scancfg->coord.height + 9155 iLineDistance) * dummyline; 9156 9157 if ((rts_coords.left & 1) == 0) 9158 rts_coords.left++; 9159 9160 RTS_Setup_Coords (Regs, rts_coords.left, rts_coords.top, 9161 rts_coords.width, rts_coords.height); 9162 9163 data_bitset (&Regs[0x01], 0x06, 0); /*-----xx-*/ 9164 9165 /* dummy_scan? */ 9166 data_bitset (&Regs[0x01], 0x10, hwdcfg->dummy_scan); /*---x----*/ 9167 9168 data_bitset (&Regs[0x163], 0xc0, 1); /*xx------ */ 9169 9170 if (dev->scanning->arrange_compression != FALSE) 9171 { 9172 Regs[0x60b] &= 0x8f; 9173 data_bitset (&Regs[0x60b], 0x10, 1); /*-001----*/ 9174 } 9175 else 9176 data_bitset (&Regs[0x60b], 0x7f, 0); /*-0000000*/ 9177 9178 if (mycolormode == 3) 9179 { 9180 SANE_Int channels_per_line; 9181 9182 /* Set channels_per_line = channels_per_dot * scan_width */ 9183 channels_per_line = 9184 data_bitget (&Regs[0x12], 0xc0) * scancfg->coord.width; 9185 data_wide_bitset (&Regs[0x060c], 0x3ffff, channels_per_line); 9186 9187 /* Sets 16 bits per channel */ 9188 data_bitset (&Regs[0x1cf], 0x30, 2); /*--10----*/ 9189 9190 Regs[0x60b] |= 0x40; 9191 if (v1619 == 0x21) 9192 { 9193 dev->scanning->arrange_compression = FALSE; 9194 data_bitset (&Regs[0x60b], 0x10, 0); /*---0----*/ 9195 } 9196 9197 switch (scancfg->depth) 9198 { 9199 case 8: 9200 case 16: 9201 Regs[0x060b] &= 0xf3; 9202 break; 9203 case 12: 9204 Regs[0x060b] = (Regs[0x060b] & 0xfb) | 0x08; 9205 break; 9206 } 9207 9208 if (scancfg->colormode == CM_LINEART) 9209 data_bitset (&Regs[0x60b], 0x0c, 0); 9210 9211 /* disable gamma correction ¿? */ 9212 data_bitset (&Regs[0x1d0], 0x40, 0); 9213 } 9214 9215 /* 5683 */ 9216 /* Set calibration table */ 9217 RTS_Setup_GainOffset (Regs, gain_offset); 9218 9219 rst = OK; 9220 } 9221 } 9222 9223 DBG (DBG_FNC, "- RTS_Setup: %i\n", rst); 9224 9225 return rst; 9226} 9227 9228static void 9229RTS_Setup_Coords (SANE_Byte * Regs, SANE_Int iLeft, SANE_Int iTop, 9230 SANE_Int width, SANE_Int height) 9231{ 9232 DBG (DBG_FNC, 9233 "> RTS_Setup_Coords(*Regs, iLeft=%i, iTop=%i, width=%i, height=%i)\n", 9234 iLeft, iTop, width, height); 9235 9236 if (Regs != NULL) 9237 { 9238 /* Set Left coord */ 9239 data_lsb_set (&Regs[0xb0], iLeft, 2); 9240 9241 /* Set Right coord */ 9242 data_lsb_set (&Regs[0xb2], iLeft + width, 2); 9243 9244 /* Set Top coord */ 9245 data_lsb_set (&Regs[0xd0], iTop, 2); 9246 data_bitset (&Regs[0xd4], 0x0f, _B2 (iTop)); 9247 9248 /* Set Down coord */ 9249 data_lsb_set (&Regs[0xd2], iTop + height, 2); 9250 data_bitset (&Regs[0xd4], 0xf0, _B2 (iTop + height)); 9251 } 9252} 9253 9254static void 9255RTS_Setup_GainOffset (SANE_Byte * Regs, struct st_gain_offset *gain_offset) 9256{ 9257 SANE_Byte fake[] = 9258 { 0x19, 0x15, 0x19, 0x64, 0x64, 0x64, 0x74, 0xc0, 0x74, 0xc0, 0x6d, 9259 0xc0, 0x6d, 0xc0, 0x5f, 0xc0, 0x5f, 0xc0 9260 }; 9261 9262 DBG (DBG_FNC, "> RTS_Setup_GainOffset(*Regs, *gain_offset)\n"); 9263 dbg_calibtable (gain_offset); 9264 9265 if ((Regs != NULL) && (gain_offset != NULL)) 9266 { 9267 if (RTS_Debug->calibrate == FALSE) 9268 { 9269 data_bitset (&Regs[0x13], 0x03, gain_offset->pag[CL_RED]); /*------xx*/ 9270 data_bitset (&Regs[0x13], 0x0c, gain_offset->pag[CL_GREEN]); /*----xx--*/ 9271 data_bitset (&Regs[0x13], 0x30, gain_offset->pag[CL_BLUE]); /*--xx----*/ 9272 9273 memcpy (&Regs[0x14], &fake, 18); 9274 } 9275 else 9276 { 9277 SANE_Int a; 9278 9279 for (a = CL_RED; a <= CL_BLUE; a++) 9280 { 9281 /* Offsets */ 9282 Regs[0x1a + (a * 4)] = _B0 (gain_offset->edcg1[a]); 9283 Regs[0x1b + (a * 4)] = 9284 ((gain_offset->edcg1[a] >> 1) & 0x80) | (gain_offset-> 9285 edcg2[a] & 0x7f); 9286 Regs[0x1c + (a * 4)] = _B0 (gain_offset->odcg1[a]); 9287 Regs[0x1d + (a * 4)] = 9288 ((gain_offset->odcg1[a] >> 1) & 0x80) | (gain_offset-> 9289 odcg2[a] & 0x7f); 9290 9291 /* Variable Gain Amplifier */ 9292 data_bitset (&Regs[0x14 + a], 0x1f, gain_offset->vgag1[a]); 9293 data_bitset (&Regs[0x17 + a], 0x1f, gain_offset->vgag2[a]); 9294 } 9295 9296 data_bitset (&Regs[0x13], 0x03, gain_offset->pag[CL_RED]); /*------xx*/ 9297 data_bitset (&Regs[0x13], 0x0c, gain_offset->pag[CL_GREEN]); /*----xx--*/ 9298 data_bitset (&Regs[0x13], 0x30, gain_offset->pag[CL_BLUE]); /*--xx----*/ 9299 } 9300 } 9301} 9302 9303static void 9304Calibrate_Free (struct st_cal2 *calbuffers) 9305{ 9306 DBG (DBG_FNC, "> Calibrate_Free(*calbuffers)\n"); 9307 9308 if (calbuffers != NULL) 9309 { 9310 SANE_Int c; 9311 9312 if (calbuffers->table2 != NULL) 9313 { 9314 free (calbuffers->table2); 9315 calbuffers->table2 = NULL; 9316 } 9317 9318 for (c = 0; c < 4; c++) 9319 { 9320 if (calbuffers->tables[c] != NULL) 9321 { 9322 free (calbuffers->tables[c]); 9323 calbuffers->tables[c] = NULL; 9324 } 9325 } 9326 9327 calbuffers->shadinglength1 = 0; 9328 calbuffers->tables_size = 0; 9329 calbuffers->shadinglength3 = 0; 9330 } 9331} 9332 9333static SANE_Int 9334Calibrate_Malloc (struct st_cal2 *calbuffers, SANE_Byte * Regs, 9335 struct st_calibration *myCalib, SANE_Int somelength) 9336{ 9337 SANE_Int myshadinglength, pos; 9338 SANE_Int rst; 9339 9340 if ((calbuffers != NULL) && (Regs != NULL) && (myCalib != NULL)) 9341 { 9342 if ((Regs[0x1bf] & 0x18) == 0) 9343 { 9344 if ((((Regs[0x1cf] >> 1) & Regs[0x1cf]) & 0x04) != 0) 9345 calbuffers->table_count = 2; 9346 else 9347 calbuffers->table_count = 4; 9348 } 9349 else 9350 calbuffers->table_count = 4; 9351 9352 /*365d */ 9353 myshadinglength = myCalib->shadinglength * 2; 9354 calbuffers->shadinglength1 = min (myshadinglength, somelength); 9355 9356 if ((myshadinglength % somelength) != 0) 9357 calbuffers->tables_size = 9358 (myshadinglength >= somelength) ? somelength * 2 : somelength; 9359 else 9360 calbuffers->tables_size = somelength; 9361 9362 if (myshadinglength >= somelength) 9363 { 9364 calbuffers->shadinglength1 = 9365 (myshadinglength % calbuffers->shadinglength1) + 9366 calbuffers->shadinglength1; 9367 calbuffers->shadinglength3 = 9368 ((myCalib->shadinglength * 2) / somelength) - 1; 9369 } 9370 else 9371 calbuffers->shadinglength3 = 0; 9372 9373 calbuffers->shadinglength3 = 9374 (somelength / 16) * calbuffers->shadinglength3; 9375 9376 rst = OK; 9377 for (pos = 0; pos < calbuffers->table_count; pos++) 9378 { 9379 calbuffers->tables[pos] = 9380 (USHORT *) malloc (calbuffers->tables_size * sizeof (USHORT)); 9381 if (calbuffers->tables[pos] == NULL) 9382 { 9383 rst = ERROR; 9384 break; 9385 } 9386 } 9387 9388 if (rst == OK) 9389 { 9390 calbuffers->table2 = 9391 (USHORT *) malloc (calbuffers->tables_size * sizeof (USHORT)); 9392 if (calbuffers->table2 == NULL) 9393 rst = ERROR; 9394 } 9395 9396 if (rst != OK) 9397 Calibrate_Free (calbuffers); 9398 } 9399 else 9400 rst = ERROR; 9401 9402 DBG (DBG_FNC, 9403 "> Calibrate_Malloc(*calbuffers, *Regs, *myCalib, somelength=%i): %i\n", 9404 somelength, rst); 9405 9406 return rst; 9407} 9408 9409static SANE_Int 9410fn3560 (USHORT * table, struct st_cal2 *calbuffers, SANE_Int * tablepos) 9411{ 9412 /*05FEF974 001F99B0 |table = 001F99B0 9413 05FEF978 05FEFA08 |calbuffers->tables[0] = 05FEFA08 9414 05FEF97C 000000A0 |calbuffers->shadinglength3 = 000000A0 9415 05FEF980 00000348 |calbuffers->shadinglength1 = 00000348 9416 05FEF984 04F01502 |calbuffers->table_count = 04F01502 9417 05FEF988 05FEF998 \Arg6 = 05FEF998 9418 */ 9419 9420 if (table != NULL) 9421 { 9422 SANE_Int pos[4] = { 0, 0, 0, 0 }; /*f960 f964 f968 f96c */ 9423 SANE_Int usetable = 0; 9424 SANE_Int a; 9425 9426 SANE_Int mylength3 = calbuffers->shadinglength1; /*f97c */ 9427 SANE_Byte *pPointer = 9428 (SANE_Byte *) (table + (calbuffers->shadinglength3 * 16)); 9429 9430 DBG (DBG_FNC, "> fn3560(*table, *calbuffers, *tablepos)\n"); 9431 9432 if (mylength3 > 0) 9433 { 9434 do 9435 { 9436 if (calbuffers->tables[usetable] != NULL) 9437 { 9438 if (mylength3 <= 16) 9439 { 9440 if (mylength3 > 0) 9441 { 9442 do 9443 { 9444 *(calbuffers->tables[usetable] + 9445 pos[usetable]) = _B0 (*pPointer); 9446 pPointer++; 9447 pos[usetable]++; 9448 mylength3--; 9449 } 9450 while (mylength3 > 0); 9451 } 9452 break; 9453 } 9454 9455 for (a = 0; a < 16; a++) 9456 { 9457 *(calbuffers->tables[usetable] + pos[usetable]) = 9458 _B0 (*pPointer); 9459 pPointer++; 9460 pos[usetable]++; 9461 } 9462 } 9463 9464 mylength3 -= 16; 9465 usetable++; 9466 if (usetable == calbuffers->table_count) 9467 usetable = 0; 9468 } 9469 while (mylength3 > 0); 9470 } 9471 9472 /*35f8 */ 9473 if (calbuffers->table_count > 0) 9474 { 9475 /* Return position of each table */ 9476 memcpy (tablepos, pos, sizeof (SANE_Int) * 4); 9477 } 9478 } 9479 9480 return OK; 9481} 9482 9483static SANE_Int 9484Calib_WriteTable (struct st_device *dev, SANE_Byte * table, SANE_Int size, 9485 SANE_Int data) 9486{ 9487 SANE_Int rst = ERROR; 9488 9489 DBG (DBG_FNC, "+ Calib_WriteTable(*table, size=%i):\n", size); 9490 9491 if ((table != NULL) && (size > 0)) 9492 { 9493 SANE_Int transferred; 9494 9495 if (RTS_DMA_Reset (dev) == OK) 9496 { 9497 /* Send size to write */ 9498 if (RTS_DMA_Enable_Write (dev, 0x0004, size, data) == OK) 9499 /* Send data */ 9500 rst = Bulk_Operation (dev, BLK_WRITE, size, table, &transferred); 9501 } 9502 } 9503 9504 DBG (DBG_FNC, "- Calib_WriteTable: %i\n", rst); 9505 9506 return rst; 9507} 9508 9509static SANE_Int 9510Calib_ReadTable (struct st_device *dev, SANE_Byte * table, SANE_Int size, 9511 SANE_Int data) 9512{ 9513 SANE_Int rst = ERROR; 9514 9515 DBG (DBG_FNC, "+ Calib_ReadTable(*table, size=%i):\n", size); 9516 9517 if ((table != NULL) && (size > 0)) 9518 { 9519 SANE_Int transferred; 9520 9521 if (RTS_DMA_Reset (dev) == OK) 9522 { 9523 /* Send size to read */ 9524 if (RTS_DMA_Enable_Read (dev, 0x0004, size, data) == OK) 9525 /* Retrieve data */ 9526 rst = Bulk_Operation (dev, BLK_READ, size, table, &transferred); 9527 } 9528 } 9529 9530 DBG (DBG_FNC, "- Calib_ReadTable: %i\n", rst); 9531 9532 return rst; 9533} 9534 9535static SANE_Int 9536fn3330 (struct st_device *dev, SANE_Byte * Regs, struct st_cal2 *calbuffers, 9537 SANE_Int sensorchannelcolor, SANE_Int * tablepos, SANE_Int data) 9538{ 9539 /*05EEF968 04F0F7F8 |Regs = 04F0F7F8 9540 05EEF96C 02DEC838 |calbuffers->table2 = 02DEC838 9541 05EEF970 05EEFA08 |calbuffers->tables[] = 05EEFA08 9542 05EEF974 00000000 |sensorchannelcolor = 00000000 9543 05EEF978 000000A0 |calbuffers->shadinglength3 = 000000A0 9544 05EEF97C 00000400 |calbuffers->tables_size = 00000400 9545 05EEF980 05EEF998 |&pos = 05EEF998 9546 05EEF984 00221502 |calbuffers->table_count = 00221502 9547 05EEF988 00000000 \data = 00000000 9548 */ 9549 9550 SANE_Int table_count = calbuffers->table_count; /*f960 */ 9551 SANE_Int schcolor = _B0 (sensorchannelcolor); 9552 SANE_Int a = 0; 9553 SANE_Int tablelength = calbuffers->shadinglength3 / table_count; /*f954 */ 9554 SANE_Int val_color = 0; /*f974 */ 9555 SANE_Int val_lineart = 0; /*f978 */ 9556 SANE_Int val_gray = 0; /*ebx */ 9557 SANE_Int value4 = 0; /*ebp */ 9558 SANE_Int size; 9559 SANE_Int rst = OK; 9560 9561 DBG (DBG_FNC, 9562 "+ fn3330(*Regs, *calbuffers, sensorchannelcolor=%i, *tablepos, data=%i):\n", 9563 sensorchannelcolor, data); 9564 9565 if (calbuffers->table_count > 0) 9566 { 9567 do 9568 { 9569 if (calbuffers->table_count == 2) 9570 { 9571 /*338c */ 9572 if (a != 0) 9573 { 9574 /*3394 */ 9575 if (_B0 (data) == 0) 9576 { 9577 val_color = 0x100000; 9578 val_lineart = 0x100000; 9579 val_gray = 0x200000; 9580 } 9581 else 9582 { 9583 /*343a */ 9584 val_color = 0x300000; 9585 val_lineart = 0x300000; 9586 val_gray = 0; 9587 } 9588 } 9589 else 9590 { 9591 /*33be */ 9592 if (_B0 (data) == 0) 9593 { 9594 val_color = 0; 9595 val_lineart = 0; 9596 val_gray = 0x300000; 9597 } 9598 else 9599 { 9600 /*342a */ 9601 val_color = 0x200000; 9602 val_lineart = 0x200000; 9603 val_gray = 0x100000; 9604 } 9605 } 9606 } 9607 else 9608 { 9609 /*33d5 */ 9610 switch (a) 9611 { 9612 case 0: 9613 val_color = 0; 9614 val_lineart = 0; 9615 val_gray = 0x300000; 9616 break; 9617 case 1: 9618 val_color = 0x200000; 9619 val_lineart = 0x200000; 9620 val_gray = 0x100000; 9621 break; 9622 case 2: 9623 val_color = 0x100000; 9624 val_lineart = 0x100000; 9625 val_gray = 0x200000; 9626 break; 9627 case 3: 9628 val_color = 0x300000; 9629 val_lineart = 0x300000; 9630 val_gray = 0; 9631 break; 9632 } 9633 } 9634 9635 /*3449 */ 9636 switch (schcolor) 9637 { 9638 case CM_LINEART: 9639 size = 9640 (((Regs[0x1bf] >> 1) & 3) << 0x10) | (Regs[0x1be] << 0x08) | 9641 Regs[0x1bd]; 9642 value4 = (tablelength + size) | val_lineart; 9643 break; 9644 case CM_GRAY: 9645 size = 9646 ((Regs[0x1bf] & 1) << 0x10) | (Regs[0x1bc] << 0x08) | 9647 Regs[0x1bb]; 9648 value4 = (tablelength + size) | val_gray; 9649 break; 9650 default: 9651 size = _B0 (Regs[0x1ba]); 9652 value4 = (tablelength + size) | val_color; 9653 break; 9654 } 9655 9656 if (Calib_ReadTable 9657 (dev, (SANE_Byte *) calbuffers->table2, calbuffers->tables_size, 9658 value4) != OK) 9659 { 9660 rst = ERROR; 9661 break; 9662 } 9663 9664 memcpy (calbuffers->tables[a], calbuffers->table2, tablepos[a]); 9665 9666 if (tablepos[a + 1] == 0) 9667 break; 9668 9669 a++; 9670 } 9671 while (a < calbuffers->table_count); 9672 } 9673 9674 DBG (DBG_FNC, "- fn3330: %i\n", rst); 9675 9676 return rst; 9677} 9678 9679static SANE_Int 9680fn3730 (struct st_device *dev, struct st_cal2 *calbuffers, SANE_Byte * Regs, 9681 USHORT * table, SANE_Int sensorchannelcolor, SANE_Int data) 9682{ 9683 /*05FEF9AC |calbuffers = 05FEF9F8 9684 05FEF9B0 |Regs = 04EFF7F8 9685 05FEF9B4 |table = 001F99B0 9686 05FEF9B8 |sensorchannelcolor = 00000000 9687 05FEF9BC |data = 00000000 9688 */ 9689 9690 SANE_Int pos[4] = { 0, 0, 0, 0 }; /*f998 f99c f9a0 f9a4 */ 9691 SANE_Int rst; 9692 9693 DBG (DBG_FNC, 9694 "+ fn3730(*calbuffers, *Regs, *table, sensorchannelcolor=%i, data=%i):\n", 9695 sensorchannelcolor, data); 9696 9697 fn3560 (table, calbuffers, pos); 9698 rst = fn3330 (dev, Regs, calbuffers, sensorchannelcolor, pos, data); 9699 9700 DBG (DBG_FNC, "- fn3730: %i\n", rst); 9701 9702 return rst; 9703} 9704 9705static SANE_Int 9706Shading_white_apply (struct st_device *dev, SANE_Byte * Regs, 9707 SANE_Int channels, struct st_calibration *myCalib, 9708 struct st_cal2 *calbuffers) 9709{ 9710 SANE_Int rst = OK; 9711 9712 DBG (DBG_FNC, "+ Shading_white_apply(channels=%i)\n", channels); 9713 9714 /*3e7f */ 9715 Calibrate_Malloc (calbuffers, Regs, myCalib, 9716 (RTS_Debug->usbtype == USB20) ? 0x200 : 0x40); 9717 9718 if (channels > 0) 9719 { 9720 /*int a; */ 9721 SANE_Int chnl; 9722 SANE_Int pos; /*fa2c */ 9723 SANE_Int transferred; 9724 9725 rst = ERROR; 9726 9727 for (chnl = 0; chnl < channels; chnl++) 9728 { 9729 /*for (a = 0; a < myCalib->shadinglength; a++) 9730 myCalib->black_shading[chnl][a] = 0x2000; */ 9731 /* 11 tries */ 9732 for (pos = 0; pos <= 10; pos++) 9733 { 9734 /* Send size to write */ 9735 if (RTS_DMA_Enable_Write 9736 (dev, dev->sensorcfg->channel_color[chnl] | 0x14, 9737 myCalib->shadinglength, 0) == OK) 9738 /* Send data */ 9739 Bulk_Operation (dev, BLK_WRITE, 9740 myCalib->shadinglength * sizeof (USHORT), 9741 (SANE_Byte *) & myCalib-> 9742 white_shading[chnl][myCalib->first_position - 9743 1], &transferred); 9744 9745 /*3df7 */ 9746 if (fn3730 9747 (dev, calbuffers, Regs, 9748 &myCalib->white_shading[chnl][myCalib->first_position - 1], 9749 dev->sensorcfg->channel_color[chnl], 1) == OK) 9750 { 9751 rst = OK; 9752 break; 9753 } 9754 9755 RTS_DMA_Cancel (dev); 9756 } 9757 } 9758 } 9759 9760 Calibrate_Free (calbuffers); 9761 9762 DBG (DBG_FNC, "- Shading_white_apply: %i\n", rst); 9763 9764 return OK; 9765} 9766 9767static SANE_Int 9768Shading_black_apply (struct st_device *dev, SANE_Byte * Regs, 9769 SANE_Int channels, struct st_calibration *myCalib, 9770 struct st_cal2 *calbuffers) 9771{ 9772 SANE_Int rst = OK; 9773 9774 DBG (DBG_FNC, "+ Shading_black_apply(channels=%i)\n", channels); 9775 9776 /* 3d79 */ 9777 Calibrate_Malloc (calbuffers, Regs, myCalib, 9778 (RTS_Debug->usbtype == USB20) ? 0x200 : 0x40); 9779 9780 if (channels > 0) 9781 { 9782 /*int a; */ 9783 SANE_Int chnl; 9784 SANE_Int pos; /*fa2c */ 9785 SANE_Int transferred; 9786 9787 rst = ERROR; 9788 9789 for (chnl = 0; chnl < channels; chnl++) 9790 { 9791 /* 11 tries */ 9792 /*for (a = 0; a < myCalib->shadinglength; a++) 9793 myCalib->black_shading[chnl][a] = 0x2000; */ 9794 9795 for (pos = 0; pos <= 10; pos++) 9796 { 9797 /* Send size to write */ 9798 if (RTS_DMA_Enable_Write 9799 (dev, dev->sensorcfg->channel_color[chnl] | 0x10, 9800 myCalib->shadinglength, 0) == OK) 9801 /* Send data */ 9802 Bulk_Operation (dev, BLK_WRITE, 9803 myCalib->shadinglength * sizeof (USHORT), 9804 (SANE_Byte *) & myCalib-> 9805 black_shading[chnl][myCalib->first_position - 9806 1], &transferred); 9807 9808 /*3df7 */ 9809 if (fn3730 9810 (dev, calbuffers, Regs, 9811 &myCalib->black_shading[chnl][myCalib->first_position - 1], 9812 dev->sensorcfg->channel_color[chnl], 0) == OK) 9813 { 9814 rst = OK; 9815 break; 9816 } 9817 9818 RTS_DMA_Cancel (dev); 9819 } 9820 } 9821 } 9822 9823 /*3e62 */ 9824 Calibrate_Free (calbuffers); 9825 9826 DBG (DBG_FNC, "- Shading_black_apply: %i\n", rst); 9827 9828 return OK; 9829} 9830 9831static SANE_Int 9832Shading_apply (struct st_device *dev, SANE_Byte * Regs, 9833 struct st_scanparams *myvar, struct st_calibration *myCalib) 9834{ 9835 /* 9836 Regs f1bc 9837 myvar f020 9838 hwdcfg e838 9839 arg4 e81c 9840 myCalib e820 9841 */ 9842 9843 SANE_Int rst; /* lf9e0 */ 9844 SANE_Int myfact; /* e820 */ 9845 SANE_Int shadata; 9846 SANE_Byte channels; /* f9d4 */ 9847 SANE_Int myShadingBase; /* e818 */ 9848 9849 char lf9d1; 9850 char lf9d0; 9851 9852 DBG (DBG_FNC, "+ Shading_apply(*Regs, *myvar, *mygamma, *myCalib):\n"); 9853 dbg_ScanParams (myvar); 9854 9855 lf9d0 = (Regs[0x60b] >> 6) & 1; 9856 lf9d1 = (Regs[0x60b] >> 4) & 1; 9857 Regs[0x060b] &= 0xaf; 9858 rst = Write_Byte (dev->usb_handle, 0xee0b, Regs[0x060b]); 9859 if (rst == OK) 9860 { 9861 SANE_Byte colormode = myvar->colormode; /*fa24 */ 9862 SANE_Int le7cc, le7d8; 9863 struct st_cal2 calbuffers; /* f9f8 */ 9864 9865 if (colormode != CM_COLOR) 9866 { 9867 if (myvar->channel != 3) 9868 { 9869 if (colormode != 3) 9870 channels = (myvar->samplerate == PIXEL_RATE) ? 2 : 1; 9871 else 9872 channels = 3; 9873 } 9874 else 9875 { 9876 colormode = 3; 9877 channels = 3; 9878 } 9879 } 9880 else 9881 channels = 3; 9882 9883 /* 9884 White shading formula : 2000H x Target / (Wn-Dn) = White Gain data ----- for 8 times system 9885 White shading formula : 4000H x Target / (Wn-Dn) = White Gain data ----- for 4 times system 9886 For example : Target = 3FFFH Wn = 2FFFH Dn = 0040H and 8 times system operation 9887 then White Gain = 2000H x 3FFFH / (2FFFH-0040H) = 2AE4H (1.34033 times) 9888 */ 9889 /* 3aad */ 9890 if (colormode == 3) 9891 { 9892 /* 9893 SANE_Int pos; 9894 SANE_Int colour; 9895 9896 myShadingBase = shadingbase; 9897 9898 for (colour = 0; colour < channels; colour++) 9899 { 9900 if (myCalib->white_shading[colour] != NULL) 9901 { 9902 myfact = shadingfact[colour]; 9903 if (myCalib->shadinglength > 0) 9904 { 9905 for (pos = myCalib->first_position - 1; pos < myCalib->shadinglength; pos++) 9906 myCalib->white_shading[colour][pos] = (myCalib->white_shading[colour][pos] * myfact) / myShadingBase; 9907 } 9908 } else break; 9909 } 9910 */ 9911 } 9912 9913 /* 3b3b */ 9914 if (myCalib->shading_enabled != FALSE) 9915 { 9916 /* 3b46 */ 9917 SANE_Int colour, pos; 9918 le7cc = shadingbase; 9919 le7d8 = shadingbase; 9920 9921 DBG (DBG_FNC, "-> Shading type: %i\n", myCalib->shading_type); 9922 9923 for (colour = 0; colour < channels; colour++) 9924 { 9925 if (colormode == 3) 9926 le7cc = shadingfact[colour]; 9927 9928 myShadingBase = ((Regs[0x1cf] & 2) != 0) ? 0x2000 : 0x4000; 9929 9930 myfact = myCalib->WRef[colour] * myShadingBase; 9931 9932 if (myCalib->shading_type == 2) 9933 { 9934 /*3bd8 */ 9935 if ((myCalib->black_shading[colour] != NULL) 9936 && (myCalib->white_shading[colour] != NULL)) 9937 { 9938 for (pos = myCalib->first_position - 1; 9939 pos < myCalib->shadinglength; pos++) 9940 { 9941 if (myCalib->white_shading[colour][pos] == 0) 9942 shadata = myShadingBase; 9943 else 9944 shadata = 9945 myfact / myCalib->white_shading[colour][pos]; 9946 9947 shadata = min ((shadata * le7cc) / le7d8, 0xff00); 9948 myCalib->black_shading[colour][pos] &= 0xff; 9949 myCalib->black_shading[colour][pos] |= 9950 shadata & 0xff00; 9951 } 9952 } 9953 else 9954 break; 9955 } 9956 else 9957 { 9958 /*3c63 */ 9959 if (myCalib->shading_type == 3) 9960 { 9961 /*3c68 */ 9962 if (myCalib->black_shading[colour] != NULL) 9963 { 9964 for (pos = myCalib->first_position - 1; 9965 pos < myCalib->shadinglength; pos++) 9966 { 9967 if (myCalib->black_shading[colour][pos] == 0) 9968 shadata = myShadingBase; 9969 else 9970 shadata = 9971 myfact / 9972 myCalib->black_shading[colour][pos]; 9973 9974 shadata = 9975 min ((shadata * le7cc) / le7d8, 0xffc0); 9976 myCalib->black_shading[colour][pos] &= 0x3f; 9977 myCalib->black_shading[colour][pos] |= 9978 shadata & 0xffc0; 9979 } 9980 } 9981 else 9982 break; 9983 } 9984 else 9985 { 9986 /*3ce3 */ 9987 if (myCalib->white_shading[colour] != NULL) 9988 { 9989 for (pos = 0; pos < myCalib->shadinglength; pos++) 9990 { 9991 if (myCalib->white_shading[colour][pos] == 0) 9992 shadata = myShadingBase; 9993 else 9994 shadata = 9995 myfact / 9996 myCalib->white_shading[colour][pos]; 9997 9998 shadata = 9999 min ((shadata * le7cc) / le7d8, 0xffff); 10000 myCalib->white_shading[colour][pos] = shadata; 10001 } 10002 } 10003 else 10004 break; 10005 } 10006 } 10007 } 10008 } 10009 10010 /*3d4c */ 10011 memset (&calbuffers, 0, sizeof (struct st_cal2)); 10012 10013 /* If black shading correction is enabled ... */ 10014 if ((Regs[0x1cf] & 8) != 0) 10015 Shading_black_apply (dev, Regs, channels, myCalib, &calbuffers); 10016 10017 /*3e6e */ 10018 10019 /* If white shading correction is enabled ... */ 10020 if ((Regs[0x1cf] & 4) != 0) 10021 Shading_white_apply (dev, Regs, channels, myCalib, &calbuffers); 10022 10023 /* 3f74 */ 10024 if (rst == 0) 10025 { 10026 data_bitset (&Regs[0x60b], 0x40, lf9d0); /*-x------*/ 10027 data_bitset (&Regs[0x60b], 0x10, lf9d1); /*---x----*/ 10028 10029 rst = Write_Byte (dev->usb_handle, 0xee0b, Regs[0x060b]); 10030 } 10031 } 10032 /*3fb5 */ 10033 10034 DBG (DBG_FNC, "- Shading_apply: %i\n", rst); 10035 10036 return rst; 10037} 10038 10039static SANE_Int 10040Bulk_Operation (struct st_device *dev, SANE_Byte op, SANE_Int buffer_size, 10041 SANE_Byte * buffer, SANE_Int * transferred) 10042{ 10043 SANE_Int iTransferSize, iBytesToTransfer, iPos, rst, iBytesTransfered; 10044 10045 DBG (DBG_FNC, "+ Bulk_Operation(op=%s, buffer_size=%i, buffer):\n", 10046 ((op & 0x01) != 0) ? "READ" : "WRITE", buffer_size); 10047 10048 iBytesToTransfer = buffer_size; 10049 iPos = 0; 10050 rst = OK; 10051 iBytesTransfered = 0; 10052 10053 if (transferred != NULL) 10054 *transferred = 0; 10055 10056 iTransferSize = min (buffer_size, RTS_Debug->dmatransfersize); 10057 10058 if (op != 0) 10059 { 10060 /* Lectura */ 10061 do 10062 { 10063 iTransferSize = min (iTransferSize, iBytesToTransfer); 10064 10065 iBytesTransfered = 10066 Read_Bulk (dev->usb_handle, &buffer[iPos], iTransferSize); 10067 if (iBytesTransfered < 0) 10068 { 10069 rst = ERROR; 10070 break; 10071 } 10072 else 10073 { 10074 if (transferred != NULL) 10075 *transferred += iBytesTransfered; 10076 } 10077 iPos += iTransferSize; 10078 iBytesToTransfer -= iTransferSize; 10079 } 10080 while (iBytesToTransfer > 0); 10081 } 10082 else 10083 { 10084 /* Escritura */ 10085 do 10086 { 10087 iTransferSize = min (iTransferSize, iBytesToTransfer); 10088 10089 if (Write_Bulk (dev->usb_handle, &buffer[iPos], iTransferSize) != 10090 OK) 10091 { 10092 rst = ERROR; 10093 break; 10094 } 10095 else 10096 { 10097 if (transferred != NULL) 10098 *transferred += iTransferSize; 10099 } 10100 iPos += iTransferSize; 10101 iBytesToTransfer -= iTransferSize; 10102 } 10103 while (iBytesToTransfer > 0); 10104 } 10105 10106 DBG (DBG_FNC, "- Bulk_Operation: %i\n", rst); 10107 10108 return rst; 10109} 10110 10111static SANE_Int 10112Reading_BufferSize_Notify (struct st_device *dev, SANE_Int data, 10113 SANE_Int size) 10114{ 10115 SANE_Int rst; 10116 10117 DBG (DBG_FNC, "+ Reading_BufferSize_Notify(data=%i, size=%i):\n", data, 10118 size); 10119 10120 rst = RTS_DMA_Enable_Read (dev, 0x0008, size, data); 10121 10122 DBG (DBG_FNC, "- Reading_BufferSize_Notify: %i\n", rst); 10123 10124 return rst; 10125} 10126 10127static SANE_Int 10128Reading_Wait (struct st_device *dev, SANE_Byte Channels_per_dot, 10129 SANE_Byte Channel_size, SANE_Int size, SANE_Int * last_amount, 10130 SANE_Int seconds, SANE_Byte op) 10131{ 10132 SANE_Int rst; 10133 SANE_Byte cTimeout, executing; 10134 SANE_Int lastAmount, myAmount; 10135 long tick; 10136 10137 DBG (DBG_FNC, 10138 "+ Reading_Wait(Channels_per_dot=%i, Channel_size=%i, size=%i, *last_amount, seconds=%i, op=%i):\n", 10139 Channels_per_dot, Channel_size, size, seconds, op); 10140 10141 rst = OK; 10142 cTimeout = FALSE; 10143 lastAmount = 0; 10144 10145 myAmount = Reading_BufferSize_Get (dev, Channels_per_dot, Channel_size); 10146 if (myAmount < size) 10147 { 10148 /* Wait until scanner fills its buffer */ 10149 if (seconds == 0) 10150 seconds = 10; 10151 tick = GetTickCount () + (seconds * 1000); 10152 10153 while (cTimeout == FALSE) 10154 { 10155 myAmount = 10156 Reading_BufferSize_Get (dev, Channels_per_dot, Channel_size); 10157 10158 /* check special case */ 10159 if (op == TRUE) 10160 { 10161 if (((myAmount + 0x450) > size) 10162 || (RTS_IsExecuting (dev, &executing) == FALSE)) 10163 break; 10164 } 10165 10166 if (myAmount < size) 10167 { 10168 /* Check timeout */ 10169 if (myAmount == lastAmount) 10170 { 10171 /* we are in timeout? */ 10172 if (tick < GetTickCount ()) 10173 { 10174 /* TIMEOUT */ 10175 rst = ERROR; 10176 cTimeout = TRUE; 10177 } 10178 else 10179 usleep (100 * 1000); 10180 } 10181 else 10182 { 10183 /* Amount increased, update tick */ 10184 lastAmount = myAmount; 10185 tick = GetTickCount () + (seconds * 1000); 10186 } 10187 } 10188 else 10189 { 10190 lastAmount = myAmount; 10191 break; /* buffer full */ 10192 } 10193 } 10194 } 10195 10196 if (last_amount != NULL) 10197 *last_amount = myAmount; 10198 10199 DBG (DBG_FNC, "- Reading_Wait: %i , last_amount=%i\n", rst, myAmount); 10200 10201 return rst; 10202} 10203 10204static SANE_Int 10205RTS_GetImage_GetBuffer (struct st_device *dev, double dSize, 10206 char unsigned *buffer, double *transferred) 10207{ 10208 SANE_Int rst = ERROR; 10209 SANE_Int itransferred; 10210 double dtransferred = 0; 10211 10212 DBG (DBG_FNC, "+ RTS_GetImage_GetBuffer(dSize=%f, buffer, transferred):\n", 10213 dSize); 10214 10215 rst = OK; 10216 dSize /= 2; 10217 10218 if (dSize > 0) 10219 { 10220 SANE_Int myLength; 10221 SANE_Int iPos = 0; 10222 10223 do 10224 { 10225 itransferred = 0; 10226 myLength = 10227 (dSize <= 10228 RTS_Debug->dmasetlength) ? dSize : RTS_Debug->dmasetlength; 10229 10230 if (myLength > 0x1ffe0) 10231 myLength = 0x1ffe0; 10232 10233 rst = ERROR; 10234 if (Reading_Wait (dev, 0, 1, myLength * 2, NULL, 5, FALSE) == OK) 10235 { 10236 if (Reading_BufferSize_Notify (dev, 0, myLength * 2) == OK) 10237 rst = 10238 Bulk_Operation (dev, BLK_READ, myLength * 2, &buffer[iPos], 10239 &itransferred); 10240 } 10241 10242 if (rst != OK) 10243 break; 10244 10245 iPos += itransferred; 10246 dSize -= itransferred; 10247 dtransferred += itransferred * 2; 10248 } 10249 while (dSize > 0); 10250 } 10251 10252 /* Return bytes transferred */ 10253 if (transferred != NULL) 10254 *transferred = dtransferred; 10255 10256 if (rst != OK) 10257 RTS_DMA_Cancel (dev); 10258 10259 DBG (DBG_FNC, "- RTS_GetImage_GetBuffer: %i\n", rst); 10260 10261 return rst; 10262} 10263 10264static SANE_Int 10265RTS_GetImage_Read (struct st_device *dev, SANE_Byte * buffer, 10266 struct st_scanparams *scancfg, struct st_hwdconfig *hwdcfg) 10267{ 10268 /*buffer f80c = esp+14 10269 scancfg f850 = esp+18 10270 hwdcfg faac = */ 10271 10272 SANE_Int rst = ERROR; 10273 10274 DBG (DBG_FNC, "+ RTS_GetImage_Read(buffer, scancfg, hwdcfg):\n"); 10275 10276 if (buffer != NULL) 10277 { 10278 double dSize = scancfg->bytesperline * scancfg->coord.height; 10279 SANE_Byte exfn; 10280 10281 if (scancfg->depth == 12) 10282 dSize = (dSize * 3) / 4; 10283 10284 /*3ff6 */ 10285 exfn = 1; 10286 if (hwdcfg != NULL) 10287 if (hwdcfg->compression != FALSE) 10288 exfn = 0; 10289 10290 if (exfn != 0) 10291 { 10292 double transferred; 10293 rst = RTS_GetImage_GetBuffer (dev, dSize, buffer, &transferred); 10294 } 10295 10296 if (rst == OK) 10297 RTS_WaitScanEnd (dev, 1500); 10298 } 10299 10300 DBG (DBG_FNC, "- RTS_GetImage_Read: %i\n", rst); 10301 10302 return rst; 10303} 10304 10305static SANE_Int 10306RTS_GetImage (struct st_device *dev, SANE_Byte * Regs, 10307 struct st_scanparams *scancfg, 10308 struct st_gain_offset *gain_offset, SANE_Byte * buffer, 10309 struct st_calibration *myCalib, SANE_Int options, 10310 SANE_Int gaincontrol) 10311{ 10312 /* 42b8e10 */ 10313 10314 SANE_Int rst = ERROR; /* default */ 10315 10316 DBG (DBG_FNC, 10317 "+ RTS_GetImage(*Regs, *scancfg, *gain_offset, *buffer, myCalib, options=0x%08x, gaincontrol=%i):\n", 10318 options, gaincontrol); 10319 dbg_ScanParams (scancfg); 10320 10321 /* validate arguments */ 10322 if ((Regs != NULL) && (scancfg != NULL)) 10323 { 10324 if ((scancfg->coord.width != 0) && (scancfg->coord.height != 0)) 10325 { 10326 struct st_scanparams *myscancfg; 10327 10328 /* let's make a copy of scan config */ 10329 myscancfg = 10330 (struct st_scanparams *) malloc (sizeof (struct st_scanparams)); 10331 if (myscancfg != NULL) 10332 { 10333 struct st_hwdconfig *hwdcfg; 10334 10335 memcpy (myscancfg, scancfg, sizeof (struct st_scanparams)); 10336 10337 /* Allocate space for low level config */ 10338 hwdcfg = 10339 (struct st_hwdconfig *) malloc (sizeof (struct st_hwdconfig)); 10340 if (hwdcfg != NULL) 10341 { 10342 memset (hwdcfg, 0, sizeof (struct st_hwdconfig)); 10343 10344 if (((options & 2) != 0) || ((_B1 (options) & 1) != 0)) 10345 { 10346 /* switch off lamp */ 10347 data_bitset (&Regs[0x146], 0x40, 0); 10348 10349 Write_Byte (dev->usb_handle, 0xe946, Regs[0x146]); 10350 usleep (1000 * ((v14b4 == 0) ? 500 : 300)); 10351 } 10352 10353 hwdcfg->scantype = scan.scantype; 10354 hwdcfg->use_gamma_tables = 10355 ((options & OP_USE_GAMMA) != 0) ? 1 : 0; 10356 hwdcfg->white_shading = 10357 ((options & OP_WHITE_SHAD) != 0) ? 1 : 0; 10358 hwdcfg->black_shading = 10359 ((options & OP_BLACK_SHAD) != 0) ? 1 : 0; 10360 hwdcfg->motor_direction = 10361 ((options & OP_BACKWARD) != 10362 0) ? MTR_BACKWARD : MTR_FORWARD; 10363 hwdcfg->compression = 10364 ((options & OP_COMPRESSION) != 0) ? 1 : 0; 10365 hwdcfg->static_head = 10366 ((options & OP_STATIC_HEAD) != 0) ? 1 : 0; 10367 hwdcfg->dummy_scan = (buffer == NULL) ? TRUE : FALSE; 10368 hwdcfg->arrangeline = 0; 10369 hwdcfg->highresolution = 10370 (myscancfg->resolution_x > 1200) ? TRUE : FALSE; 10371 hwdcfg->unk3 = 0; 10372 10373 /* Set Left coord */ 10374 myscancfg->coord.left += 10375 ((dev->sensorcfg->type == CCD_SENSOR) ? 24 : 50); 10376 10377 switch (myscancfg->resolution_x) 10378 { 10379 case 1200: 10380 myscancfg->coord.left -= 63; 10381 break; 10382 case 2400: 10383 myscancfg->coord.left -= 126; 10384 break; 10385 } 10386 10387 if (myscancfg->coord.left < 0) 10388 myscancfg->coord.left = 0; 10389 10390 RTS_Setup (dev, Regs, myscancfg, hwdcfg, gain_offset); 10391 10392 /* Setting exposure time */ 10393 switch (scan.scantype) 10394 { 10395 case ST_NORMAL: 10396 if (scan.resolution_x == 100) 10397 { 10398 SANE_Int iValue; 10399 SANE_Byte *myRegs; 10400 10401 myRegs = 10402 (SANE_Byte *) malloc (RT_BUFFER_LEN * 10403 sizeof (SANE_Byte)); 10404 if (myRegs != NULL) 10405 { 10406 memset (myRegs, 0, 10407 RT_BUFFER_LEN * sizeof (SANE_Byte)); 10408 RTS_Setup (dev, myRegs, &scan, hwdcfg, 10409 gain_offset); 10410 10411 iValue = data_lsb_get (&myRegs[0x30], 3); 10412 data_lsb_set (&Regs[0x30], iValue, 3); 10413 10414 /*Copy myregisters mexpts to Regs mexpts */ 10415 iValue = data_lsb_get (&myRegs[0x33], 3); 10416 data_lsb_set (&Regs[0x33], iValue, 3); 10417 10418 iValue = data_lsb_get (&myRegs[0x39], 3); 10419 data_lsb_set (&Regs[0x39], iValue, 3); 10420 10421 iValue = data_lsb_get (&myRegs[0x3f], 3); 10422 data_lsb_set (&Regs[0x3f], iValue, 3); 10423 10424 free (myRegs); 10425 } 10426 } 10427 break; 10428 case ST_NEG: 10429 { 10430 SANE_Int myvalue; 10431 10432 /* Setting exposure times for Negative scans */ 10433 data_lsb_set (&Regs[0x30], myscancfg->expt, 3); 10434 data_lsb_set (&Regs[0x33], myscancfg->expt, 3); 10435 data_lsb_set (&Regs[0x39], myscancfg->expt, 3); 10436 data_lsb_set (&Regs[0x3f], myscancfg->expt, 3); 10437 10438 data_lsb_set (&Regs[0x36], 0, 3); 10439 data_lsb_set (&Regs[0x3c], 0, 3); 10440 data_lsb_set (&Regs[0x42], 0, 3); 10441 10442 myvalue = 10443 ((myscancfg->expt + 10444 1) / (data_lsb_get (&Regs[0xe0], 1) + 1)) - 1; 10445 data_lsb_set (&Regs[0xe1], myvalue, 3); 10446 } 10447 break; 10448 } 10449 10450 /* 91a0 */ 10451 if (myscancfg->resolution_y > 600) 10452 { 10453 options |= 0x20000000; 10454 if (options != 0) /* Always true ... */ 10455 SetMultiExposure (dev, Regs); 10456 else 10457 myscancfg->coord.top += hwdcfg->startpos; 10458 } 10459 else 10460 SetMultiExposure (dev, Regs); 10461 10462 /* 91e2 */ 10463 RTS_WriteRegs (dev->usb_handle, Regs); 10464 if (myCalib != NULL) 10465 Shading_apply (dev, Regs, myscancfg, myCalib); 10466 10467 if (dev->motorcfg->changemotorcurrent != FALSE) 10468 Motor_Change (dev, Regs, 10469 Motor_GetFromResolution (myscancfg-> 10470 resolution_x)); 10471 10472 /* mlock = 0 */ 10473 data_bitset (&Regs[0x00], 0x10, 0); 10474 10475 data_wide_bitset (&Regs[0xde], 0xfff, 0); 10476 10477 /* release motor */ 10478 Motor_Release (dev); 10479 10480 if (RTS_Warm_Reset (dev) == OK) 10481 { 10482 rst = OK; 10483 10484 SetLock (dev->usb_handle, Regs, 10485 (myscancfg->depth == 16) ? FALSE : TRUE); 10486 10487 /* set gain control */ 10488 Lamp_SetGainMode (dev, Regs, myscancfg->resolution_x, 10489 gaincontrol); 10490 10491 /* send registers to scanner */ 10492 if (RTS_WriteRegs (dev->usb_handle, Regs) == OK) 10493 { 10494 /* execute! */ 10495 if (RTS_Execute (dev) == OK) 10496 RTS_GetImage_Read (dev, buffer, myscancfg, hwdcfg); /*92e7 */ 10497 } 10498 10499 /*92fc */ 10500 SetLock (dev->usb_handle, Regs, FALSE); 10501 10502 if ((options & 0x200) != 0) 10503 { 10504 /* switch on lamp */ 10505 data_bitset (&Regs[0x146], 0x40, 1); 10506 10507 Write_Byte (dev->usb_handle, 0xe946, Regs[0x146]); 10508 /* Wait 3 seconds */ 10509 usleep (1000 * 3000); 10510 } 10511 10512 /*9351 */ 10513 if (dev->motorcfg->changemotorcurrent == TRUE) 10514 Motor_Change (dev, dev->init_regs, 3); 10515 } 10516 10517 /* free low level configuration */ 10518 free (hwdcfg); 10519 } 10520 10521 /* free scanning configuration */ 10522 free (myscancfg); 10523 } 10524 } 10525 } 10526 10527 DBG (DBG_FNC, "- RTS_GetImage: %i\n", rst); 10528 10529 return rst; 10530} 10531 10532static SANE_Int 10533Refs_Detect (struct st_device *dev, SANE_Byte * Regs, SANE_Int resolution_x, 10534 SANE_Int resolution_y, SANE_Int * x, SANE_Int * y) 10535{ 10536 SANE_Int rst = ERROR; /* default */ 10537 10538 DBG (DBG_FNC, "+ Refs_Detect(*Regs, resolution_x=%i, resolution_y=%i):\n", 10539 resolution_x, resolution_y); 10540 10541 if ((x != NULL) && (y != NULL)) 10542 { 10543 SANE_Byte *image; 10544 struct st_scanparams scancfg; 10545 10546 *x = *y = 0; /* default */ 10547 10548 /* set configuration to scan a little area at the top-left corner */ 10549 memset (&scancfg, 0, sizeof (struct st_scanparams)); 10550 scancfg.depth = 8; 10551 scancfg.colormode = CM_GRAY; 10552 scancfg.channel = CL_RED; 10553 scancfg.resolution_x = resolution_x; 10554 scancfg.resolution_y = resolution_y; 10555 scancfg.coord.left = 4; 10556 scancfg.coord.width = (resolution_x * 3) / 10; 10557 scancfg.coord.top = 1; 10558 scancfg.coord.height = (resolution_y * 4) / 10; 10559 scancfg.shadinglength = (resolution_x * 17) / 2; 10560 scancfg.bytesperline = scancfg.coord.width; 10561 10562 /* allocate space to store image */ 10563 image = 10564 (SANE_Byte *) malloc ((scancfg.coord.height * scancfg.coord.width) * 10565 sizeof (SANE_Byte)); 10566 if (image != NULL) 10567 { 10568 struct st_gain_offset gain_offset; 10569 SANE_Int gaincontrol, pwmlamplevel_backup, C; 10570 10571 gaincontrol = 0; 10572 if (RTS_Debug->use_fixed_pwm == FALSE) 10573 { 10574 /* 3877 */ 10575 gaincontrol = Lamp_GetGainMode (dev, resolution_x, ST_NORMAL); /* scan.scantype */ 10576 pwmlamplevel = 0; 10577 Lamp_PWM_use (dev, 1); 10578 Lamp_PWM_DutyCycle_Set (dev, (gaincontrol == 0) ? 0x12 : 0x26); 10579 10580 /* Enciende flb lamp */ 10581 Lamp_Status_Set (dev, NULL, TRUE, FLB_LAMP); 10582 usleep (1000 * 2000); 10583 } 10584 10585 /* 38d6 */ 10586 pwmlamplevel_backup = pwmlamplevel; 10587 pwmlamplevel = 0; 10588 Lamp_PWM_use (dev, 1); 10589 10590 memset (&gain_offset, 0, sizeof (struct st_gain_offset)); 10591 for (C = CL_RED; C <= CL_BLUE; C++) 10592 { 10593 gain_offset.pag[C] = 3; 10594 gain_offset.vgag1[C] = 4; 10595 gain_offset.vgag2[C] = 4; 10596 } 10597 10598 /* perform lamp warmup */ 10599 Lamp_Warmup (dev, Regs, FLB_LAMP, resolution_x); 10600 10601 /* retrieve image from scanner */ 10602 if (RTS_GetImage 10603 (dev, Regs, &scancfg, &gain_offset, image, 0, 0x20000000, 10604 gaincontrol) == OK) 10605 { 10606 SANE_Int ser1, ler1; 10607 10608 /* same image to disk if required by user */ 10609 if (RTS_Debug->SaveCalibFile != FALSE) 10610 { 10611 dbg_tiff_save ("pre-autoref.tiff", 10612 scancfg.coord.width, 10613 scancfg.coord.height, 10614 scancfg.depth, 10615 CM_GRAY, 10616 scancfg.resolution_x, 10617 scancfg.resolution_y, 10618 image, 10619 scancfg.coord.height * scancfg.coord.width); 10620 } 10621 10622 /* calculate reference position */ 10623 if (Refs_Analyze_Pattern (&scancfg, image, &ler1, 1, &ser1, 0) 10624 == OK) 10625 { 10626 *y = scancfg.coord.top + ler1; 10627 *x = scancfg.coord.left + ser1; 10628 10629 rst = OK; 10630 } 10631 } 10632 10633 free (image); 10634 10635 pwmlamplevel = pwmlamplevel_backup; 10636 } 10637 10638 DBG (DBG_FNC, " -> Detected refs: x=%i , y=%i\n", *x, *y); 10639 } 10640 10641 DBG (DBG_FNC, "- Refs_Detect: %i\n", rst); 10642 10643 return rst; 10644} 10645 10646static SANE_Int 10647Refs_Set (struct st_device *dev, SANE_Byte * Regs, 10648 struct st_scanparams *scancfg) 10649{ 10650 SANE_Int rst; 10651 SANE_Int y, x; 10652 struct st_autoref refcfg; 10653 10654 DBG (DBG_FNC, "+ Refs_Set(*Regs, *scancfg):\n"); 10655 dbg_ScanParams (scancfg); 10656 10657 rst = OK; 10658 10659 /* get fixed references for given resolution */ 10660 cfg_vrefs_get (dev->sensorcfg->type, scancfg->resolution_x, &scan.ler, 10661 &scan.ser); 10662 scan.leftleading = scan.ser; 10663 scan.startpos = scan.ler; 10664 10665 /* get auto reference configuration */ 10666 cfg_autoref_get (&refcfg); 10667 10668 if (refcfg.type != REF_NONE) 10669 { 10670 /* if reference counter is == 0 perform auto detection */ 10671 if (Refs_Counter_Load (dev) == 0) 10672 { 10673 DBG (DBG_FNC, 10674 " -> Refs_Set - Autodetection mandatory (counter == 0)\n"); 10675 10676 refcfg.type = REF_AUTODETECT; 10677 } 10678 10679 switch (refcfg.type) 10680 { 10681 case REF_AUTODETECT: 10682 /* try to autodetect references scanning a little area */ 10683 if (Refs_Detect 10684 (dev, Regs, refcfg.resolution, refcfg.resolution, &x, &y) == OK) 10685 Refs_Save (dev, x, y); 10686 else 10687 rst = ERROR; 10688 10689 Head_ParkHome (dev, TRUE, dev->motorcfg->parkhomemotormove); 10690 break; 10691 10692 case REF_TAKEFROMSCANNER: 10693 /* Try to get values from scanner */ 10694 if (Refs_Load (dev, &x, &y) == ERROR) 10695 { 10696 if (Refs_Detect 10697 (dev, Regs, refcfg.resolution, refcfg.resolution, &x, 10698 &y) == OK) 10699 Refs_Save (dev, x, y); 10700 else 10701 rst = ERROR; 10702 10703 Head_ParkHome (dev, TRUE, dev->motorcfg->parkhomemotormove); 10704 } 10705 break; 10706 } 10707 10708 if (rst == OK) 10709 { 10710 /* values are based on resolution given by refcfg.resolution. 10711 10712 offset_x and y are based on 2400 dpi so convert values to that dpi 10713 before adding offsets and then return to resolution given by user */ 10714 10715 x *= (2400 / refcfg.resolution); 10716 y *= (2400 / refcfg.resolution); 10717 10718 scan.leftleading = x; 10719 scan.startpos = y; 10720 scan.ser = ((x + refcfg.offset_x) * scancfg->resolution_x) / 2400; 10721 scan.ler = ((y + refcfg.offset_y) * scancfg->resolution_y) / 2400; 10722 10723 DBG (DBG_FNC, 10724 " -> After SEROffset and LEROffset, xoffset = %i, yoffset =%i\n", 10725 scan.ser, scan.ler); 10726 } 10727 10728 /* increase refs counter */ 10729 Refs_Counter_Inc (dev); 10730 } 10731 10732 DBG (DBG_FNC, "- Refs_Set: %i\n", rst); 10733 10734 return rst; 10735} 10736 10737static SANE_Int 10738Lamp_Status_Set (struct st_device *dev, SANE_Byte * Regs, SANE_Int turn_on, 10739 SANE_Int lamp) 10740{ 10741 SANE_Int rst = ERROR; /* default */ 10742 SANE_Byte freevar = FALSE; 10743 10744 DBG (DBG_FNC, "+ Lamp_Status_Set(*Regs, turn_on=%i->%s, lamp=%s)\n", 10745 turn_on, 10746 ((((lamp - 1) | turn_on) & 1) == 1) ? "Yes" : "No", 10747 (lamp == FLB_LAMP) ? "FLB_LAMP" : "TMA_LAMP"); 10748 10749 if (Regs == NULL) 10750 { 10751 Regs = (SANE_Byte *) malloc (RT_BUFFER_LEN * sizeof (SANE_Byte)); 10752 10753 if (Regs != NULL) 10754 freevar = TRUE; 10755 } 10756 10757 if (Regs != NULL) 10758 { 10759 RTS_ReadRegs (dev->usb_handle, Regs); 10760 10761 /* next op depends on chipset */ 10762 switch (dev->chipset->model) 10763 { 10764 case RTS8822BL_03A: 10765 /* register 0xe946 has 2 bits and each one refers one lamp 10766 0x40: FLB_LAMP | 0x20 : TMA_LAMP 10767 if both were enabled both lamps would be switched on */ 10768 data_bitset (&Regs[0x146], 0x20, ((lamp == TMA_LAMP) && (turn_on == TRUE)) ? 1 : 0); /* TMA */ 10769 data_bitset (&Regs[0x146], 0x40, ((lamp == FLB_LAMP) && (turn_on == TRUE)) ? 1 : 0); /* FLB */ 10770 10771 data_bitset (&Regs[0x155], 0x10, (lamp != FLB_LAMP) ? 1 : 0); 10772 break; 10773 default: 10774 /* the other chipsets only use one bit to indicate when a lamp is 10775 switched on or not being bit 0x10 in 0xe955 who decides which lamp 10776 is affected */ 10777 /* switch on lamp? yes if TMA_LAMP, else whatever turn_on says */ 10778 data_bitset (&Regs[0x146], 0x40, ((lamp - 1) | turn_on)); 10779 /* what lamp must be switched on? */ 10780 if ((Regs[0x146] & 0x40) != 0) 10781 data_bitset (&Regs[0x155], 0x10, (lamp != FLB_LAMP) ? 1 : 0); 10782 break; 10783 } 10784 10785 /*42b8cd1 */ 10786 /* switch on/off lamp */ 10787 /*dev->init_regs[0x0146] = (dev->init_regs[0x146] & 0xbf) | (Regs[0x146] & 0x40); */ 10788 dev->init_regs[0x0146] = (dev->init_regs[0x146] & 0x9f) | (Regs[0x146] & 0x60); /*-xx-----*/ 10789 10790 /* Which lamp */ 10791 dev->init_regs[0x0155] = Regs[0x0155]; 10792 Write_Byte (dev->usb_handle, 0xe946, Regs[0x0146]); 10793 usleep (1000 * 200); 10794 Write_Buffer (dev->usb_handle, 0xe954, &Regs[0x0154], 2); 10795 } 10796 10797 if (freevar != FALSE) 10798 { 10799 free (Regs); 10800 Regs = NULL; 10801 } 10802 10803 DBG (DBG_FNC, "- Lamp_Status_Set: %i\n", rst); 10804 10805 return rst; 10806} 10807 10808static SANE_Int 10809Get_PAG_Value (SANE_Byte scantype, SANE_Byte color) 10810{ 10811 SANE_Int rst, iType, iColor; 10812 10813 switch (scantype) 10814 { 10815 case ST_NEG: 10816 iType = CALIBNEGATIVEFILM; 10817 break; 10818 case ST_TA: 10819 iType = CALIBTRANSPARENT; 10820 break; 10821 case ST_NORMAL: 10822 iType = CALIBREFLECTIVE; 10823 break; 10824 default: 10825 iType = CALIBREFLECTIVE; 10826 break; 10827 } 10828 10829 switch (color) 10830 { 10831 case CL_BLUE: 10832 iColor = PAGB; 10833 break; 10834 case CL_GREEN: 10835 iColor = PAGG; 10836 break; 10837 case CL_RED: 10838 iColor = PAGR; 10839 break; 10840 default: 10841 iColor = PAGR; 10842 break; 10843 } 10844 10845 rst = get_value (iType, iColor, 1, FITCALIBRATE); 10846 10847 DBG (DBG_FNC, "> Get_PAG_Value(scantype=%s, color=%i): %i\n", 10848 dbg_scantype (scantype), color, rst); 10849 10850 return rst; 10851} 10852 10853static SANE_Byte 10854Lamp_GetGainMode (struct st_device *dev, SANE_Int resolution, 10855 SANE_Byte scantype) 10856{ 10857 SANE_Byte ret; 10858 SANE_Int mygain, iValue; 10859 10860 switch (scantype) 10861 { 10862 case ST_TA: 10863 ret = 0; 10864 iValue = DPIGAINCONTROL_TA600; 10865 break; 10866 case ST_NEG: 10867 ret = 1; 10868 iValue = DPIGAINCONTROL_NEG600; 10869 break; 10870 default: /* Reflective */ 10871 ret = 1; 10872 iValue = DPIGAINCONTROL600; 10873 break; 10874 } 10875 10876 mygain = get_value (SCAN_PARAM, iValue, ret, usbfile); 10877 ret = 0; 10878 10879/* 10880 10881*/ 10882 if (scantype == ST_NORMAL) 10883 { 10884 if (dev->chipset->model == RTS8822L_02A) 10885 { 10886 switch (resolution) 10887 { 10888 case 100: 10889 case 150: 10890 case 300: 10891 case 600: 10892 case 1200: 10893 case 2400: 10894 case 4800: 10895 ret = ((RTS_Debug->usbtype != USB11) && (mygain != 0)) ? 1 : 0; 10896 break; 10897 } 10898 } 10899 else 10900 { 10901 switch (resolution) 10902 { 10903 case 100: 10904 case 200: 10905 case 300: 10906 case 600: 10907 if (RTS_Debug->usbtype != USB11) 10908 ret = (mygain != 0) ? 1 : 0; 10909 else 10910 ret = (resolution == 100) ? 1 : 0; 10911 break; 10912 case 1200: 10913 case 2400: 10914 ret = 0; 10915 break; 10916 } 10917 } 10918 } 10919 else if (scantype == ST_TA) 10920 { 10921 switch (resolution) 10922 { 10923 /*hp3970 */ 10924 case 100: 10925 case 200: 10926 /*common */ 10927 case 300: 10928 case 600: 10929 case 1200: 10930 case 2400: 10931 /*hp4370 */ 10932 case 150: 10933 case 4800: 10934 ret = ((RTS_Debug->usbtype != USB11) && (mygain != 0)) ? 1 : 0; 10935 break; 10936 } 10937 } 10938 else 10939 { 10940 /* ST_NEG */ 10941 switch (resolution) 10942 { 10943 case 100: 10944 case 200: 10945 case 300: 10946 case 600: 10947 ret = ((RTS_Debug->usbtype != USB11) && (mygain != 0)) ? 1 : 0; 10948 break; 10949 case 1200: 10950 case 2400: 10951 case 4800: /*hp4370 */ 10952 ret = 0; 10953 break; 10954 } 10955 } 10956 10957 DBG (DBG_FNC, "> Lamp_GetGainMode(resolution=%i, scantype=%s): %i\n", 10958 resolution, dbg_scantype (scantype), ret); 10959 10960 return ret; 10961} 10962 10963static SANE_Int 10964GetOneLineInfo (struct st_device *dev, SANE_Int resolution, 10965 SANE_Int * maximus, SANE_Int * minimus, double *average) 10966{ 10967 SANE_Int rst = ERROR; 10968 10969 DBG (DBG_FNC, 10970 "+ GetOneLineInfo(resolution=%i, *maximus, *minimus, *average):\n", 10971 resolution); 10972 10973 /* Check parameters */ 10974 if ((maximus != NULL) && (minimus != NULL) && (average != NULL)) 10975 { 10976 SANE_Byte *Regs, *image; 10977 SANE_Int a, gainmode; 10978 struct st_gain_offset gain_offset; 10979 struct st_scanparams scancfg; 10980 10981 Regs = (SANE_Byte *) malloc (RT_BUFFER_LEN * sizeof (SANE_Byte)); 10982 if (Regs != NULL) 10983 { 10984 /* Copy scanner registers */ 10985 memcpy (Regs, dev->init_regs, RT_BUFFER_LEN * sizeof (SANE_Byte)); 10986 10987 /* Setting some registers */ 10988 for (a = 0x192; a <= 0x19d; a++) 10989 Regs[a] = 0; 10990 10991 /* Create calibration table */ 10992 for (a = CL_RED; a <= CL_BLUE; a++) 10993 { 10994 gain_offset.edcg1[a] = 256; 10995 gain_offset.edcg2[a] = 0; 10996 gain_offset.odcg1[a] = 256; 10997 gain_offset.odcg2[a] = 0; 10998 gain_offset.vgag1[a] = 4; 10999 gain_offset.vgag2[a] = 4; 11000 gain_offset.pag[a] = Get_PAG_Value (scan.scantype, a); 11001 } 11002 11003 RTS_GetScanmode (dev, scantype, 0, resolution); 11004 11005 /* Setting scanning params */ 11006 memset (&scancfg, 0, sizeof (struct st_scanparams)); 11007 scancfg.colormode = CM_COLOR; 11008 scancfg.resolution_x = resolution; 11009 scancfg.resolution_y = resolution; 11010 scancfg.coord.left = 100; 11011 scancfg.coord.width = (resolution * 8.5) - 100; 11012 scancfg.coord.top = 1; 11013 scancfg.coord.height = 1; 11014 scancfg.depth = 8; 11015 scancfg.shadinglength = resolution * 8.5; 11016 scancfg.v157c = scancfg.coord.width * 3; 11017 scancfg.bytesperline = scancfg.v157c; 11018 11019 /* Reserve buffer for line */ 11020 image = 11021 (SANE_Byte *) malloc (((scancfg.coord.width * 0x21) * 3) * 11022 sizeof (SANE_Byte)); 11023 if (image != NULL) 11024 { 11025 gainmode = 11026 Lamp_GetGainMode (dev, resolution & 0xffff, scan.scantype); 11027 if (RTS_GetImage 11028 (dev, Regs, &scancfg, &gain_offset, image, 0, 11029 OP_STATIC_HEAD, gainmode) != ERROR) 11030 { 11031 /* Read all image to take max min and average colours */ 11032 SANE_Byte *pointer1 = image; 11033 SANE_Byte *pointer2; 11034 SANE_Byte *pointer3; 11035 SANE_Int cmin[3]; /* min values */ 11036 SANE_Int cmax[3]; /* max values */ 11037 double cave[3]; /* average values */ 11038 SANE_Int mysize; 11039 11040 if (scancfg.colormode != CM_GRAY) 11041 { 11042 pointer2 = image; 11043 pointer3 = image; 11044 } 11045 else 11046 { 11047 pointer2 = image + 1; 11048 pointer3 = image + 2; 11049 } 11050 11051 for (a = CL_RED; a <= CL_BLUE; a++) 11052 { 11053 cmin[a] = 255; 11054 cmax[a] = 0; 11055 cave[a] = 0; 11056 } 11057 11058 if (scancfg.coord.height > 0) 11059 { 11060 SANE_Int y, x; 11061 SANE_Byte *mypointer; 11062 SANE_Byte color; 11063 SANE_Int desp[3]; 11064 11065 desp[CL_RED] = pointer1 - pointer3; 11066 desp[CL_GREEN] = pointer2 - pointer3; 11067 desp[CL_BLUE] = 0; 11068 11069 for (y = 0; y < scancfg.coord.height; y++) 11070 { 11071 if (scancfg.coord.width > 0) 11072 { 11073 mypointer = pointer3; 11074 11075 for (x = 0; x < scancfg.coord.width; x++) 11076 { 11077 for (a = CL_RED; a <= CL_BLUE; a++) 11078 { 11079 /* Take colour values */ 11080 color = *(mypointer + desp[a]); 11081 11082 /* Take max values for each color */ 11083 cmax[a] = max (cmax[a], color); 11084 11085 /* Take min values for each color */ 11086 cmin[a] = min (cmin[a], color); 11087 11088 /* Average */ 11089 cave[a] += color; 11090 } 11091 11092 mypointer += 3; 11093 } 11094 } 11095 11096 /* point to the pixel that is below */ 11097 pointer1 += scancfg.coord.width * 3; 11098 pointer2 += scancfg.coord.width * 3; 11099 pointer3 += scancfg.coord.width * 3; 11100 } 11101 } 11102 11103 mysize = scancfg.coord.height * scancfg.coord.width; 11104 if (mysize < 1) 11105 mysize = 1; 11106 11107 for (a = CL_RED; a <= CL_BLUE; a++) 11108 { 11109 maximus[a] = cmax[a]; 11110 minimus[a] = cmin[a]; 11111 average[a] = cave[a] / mysize; 11112 } 11113 11114 DBG (DBG_FNC, " -> GetOneLineInfo: max r=%3i g=%3i b=%3i\n", 11115 maximus[CL_RED], maximus[CL_GREEN], maximus[CL_BLUE]); 11116 DBG (DBG_FNC, " -> min r=%3i g=%3i b=%3i\n", 11117 minimus[CL_RED], minimus[CL_GREEN], minimus[CL_BLUE]); 11118 DBG (DBG_FNC, 11119 " -> avg r=%3.0f g=%3.0f b=%3.0f\n", 11120 average[CL_RED], average[CL_GREEN], average[CL_BLUE]); 11121 11122 rst = OK; 11123 } 11124 11125 free (image); 11126 } 11127 11128 free (Regs); 11129 } 11130 } 11131 11132 DBG (DBG_FNC, "- GetOneLineInfo: %i\n", rst); 11133 11134 return OK; 11135} 11136 11137static SANE_Int 11138Lamp_PWM_CheckStable (struct st_device *dev, SANE_Int resolution, 11139 SANE_Int lamp) 11140{ 11141 struct st_checkstable check; 11142 SANE_Int rst; 11143 11144 DBG (DBG_FNC, "+ Lamp_PWM_CheckStable(resolution=%i, lamp=%i):\n", 11145 resolution, lamp); 11146 11147 rst = cfg_checkstable_get (lamp, &check); 11148 11149 if (rst == OK) 11150 { 11151 SANE_Int maximus[3] = { 0 }; 11152 SANE_Int minimus[3] = { 0 }; 11153 double average[3] = { 0 }; 11154 SANE_Int maxbigger; 11155 SANE_Int last_colour = 0; 11156 11157 double diff = check.diff * 0.01; 11158 long tottime = GetTickCount () + check.tottime; 11159 11160 while (GetTickCount () <= tottime) 11161 { 11162 rst = GetOneLineInfo (dev, resolution, maximus, minimus, average); 11163 if (rst == OK) 11164 { 11165 /* Takes maximal colour value */ 11166 maxbigger = 11167 max (maximus[CL_GREEN], 11168 max (maximus[CL_BLUE], maximus[CL_RED])); 11169 11170 /*breaks when colour intensity increases 'diff' or lower */ 11171 if (abs (maxbigger - last_colour) < diff) 11172 { 11173 DBG (DBG_FNC, " -> PWM is ready\n"); 11174 break; 11175 } 11176 11177 last_colour = maxbigger; 11178 } 11179 11180 usleep (1000 * check.interval); 11181 } 11182 11183 } 11184 11185 DBG (DBG_FNC, "- Lamp_PWM_CheckStable: %i\n", rst); 11186 11187 return OK; 11188} 11189 11190static SANE_Byte 11191Refs_Counter_Load (struct st_device *dev) 11192{ 11193 SANE_Byte data = 15; 11194 11195 DBG (DBG_FNC, "+ Refs_Counter_Load:\n"); 11196 11197 /* check if chipset supports accessing eeprom */ 11198 if ((dev->chipset->capabilities & CAP_EEPROM) != 0) 11199 if (RTS_EEPROM_ReadByte (dev->usb_handle, 0x78, &data) != OK) 11200 data = 15; 11201 11202 DBG (DBG_FNC, "- Refs_Counter_Load: %i\n", _B0 (data)); 11203 11204 return data; 11205} 11206 11207static SANE_Int 11208Refs_Counter_Save (struct st_device *dev, SANE_Byte data) 11209{ 11210 SANE_Int rst = OK; 11211 11212 DBG (DBG_FNC, "+ Refs_Counter_Save(data=%i):\n", data); 11213 11214 /* check if chipset supports accessing eeprom */ 11215 if ((dev->chipset->capabilities & CAP_EEPROM) != 0) 11216 { 11217 if (data > 15) 11218 data = 15; 11219 11220 rst = RTS_EEPROM_WriteByte (dev->usb_handle, 0x78, data); 11221 } 11222 11223 DBG (DBG_FNC, "- Refs_Counter_Save: %i\n", rst); 11224 11225 return rst; 11226} 11227 11228static SANE_Int 11229Refs_Counter_Inc (struct st_device *dev) 11230{ 11231 SANE_Byte data; 11232 11233 DBG (DBG_FNC, "+ Refs_Counter_Inc:\n"); 11234 11235 data = Refs_Counter_Load (dev) + 1; 11236 11237 if (data >= 15) 11238 data = 0; 11239 11240 Refs_Counter_Save (dev, data); 11241 11242 DBG (DBG_FNC, "- Refs_Counter_Inc() : Count=%i\n", data); 11243 11244 return OK; 11245} 11246 11247static SANE_Int 11248Load_StripCoords (SANE_Int scantype, SANE_Int * ypos, SANE_Int * xpos) 11249{ 11250 SANE_Int iType; 11251 11252 switch (scantype) 11253 { 11254 case 3: 11255 iType = CALIBNEGATIVEFILM; 11256 break; 11257 case 2: 11258 iType = CALIBTRANSPARENT; 11259 break; 11260 default: 11261 iType = CALIBREFLECTIVE; 11262 break; 11263 } 11264 11265 *xpos = get_value (iType, WSTRIPXPOS, 0, FITCALIBRATE); 11266 *ypos = get_value (iType, WSTRIPYPOS, 0, FITCALIBRATE); 11267 11268 DBG (DBG_FNC, "> Load_StripCoords(scantype=%s): ypos=%i, xpos=%i\n", 11269 dbg_scantype (scantype), *ypos, *xpos); 11270 11271 return OK; 11272} 11273 11274static SANE_Int 11275Head_Relocate (struct st_device *dev, SANE_Int speed, SANE_Int direction, 11276 SANE_Int ypos) 11277{ 11278 SANE_Int rst; 11279 SANE_Byte *Regs; 11280 11281 DBG (DBG_FNC, "+ Head_Relocate(speed=%i, direction=%i, ypos=%i):\n", speed, 11282 direction, ypos); 11283 11284 rst = ERROR; 11285 11286 Regs = (SANE_Byte *) malloc (RT_BUFFER_LEN * sizeof (SANE_Byte)); 11287 if (Regs != NULL) 11288 { 11289 struct st_motormove mymotor; 11290 struct st_motorpos mtrpos; 11291 11292 memset (&mymotor, 0, sizeof (struct st_motormove)); 11293 memcpy (Regs, dev->init_regs, RT_BUFFER_LEN * sizeof (SANE_Byte)); 11294 11295 if (speed < dev->motormove_count) 11296 memcpy (&mymotor, dev->motormove[speed], 11297 sizeof (struct st_motormove)); 11298 11299 /*83fe */ 11300 mtrpos.coord_y = ypos; 11301 mtrpos.options = 11302 MTR_ENABLED | ((direction == MTR_BACKWARD) ? MTR_BACKWARD : 11303 MTR_FORWARD); 11304 mtrpos.v12e448 = 0; 11305 mtrpos.v12e44c = 1; 11306 11307 Motor_Move (dev, Regs, &mymotor, &mtrpos); 11308 11309 /* waits 15 seconds */ 11310 RTS_WaitScanEnd (dev, 15000); 11311 11312 free (Regs); 11313 rst = OK; 11314 } 11315 11316 DBG (DBG_FNC, "- Head_Relocate: %i\n", rst); 11317 11318 return rst; 11319} 11320 11321static SANE_Int 11322Calib_CreateFixedBuffers () 11323{ 11324 SANE_Byte channel; 11325 SANE_Int ret; 11326 11327 DBG (DBG_FNC, "> Calib_CreateFixedBuffers()\n"); 11328 11329 ret = OK; 11330 channel = 0; 11331 11332 while ((channel < 3) && (ret == OK)) 11333 { 11334 /* First table */ 11335 if (fixed_black_shading[channel] == NULL) 11336 fixed_black_shading[channel] = 11337 (USHORT *) malloc (0x7f8 * sizeof (USHORT)); 11338 11339 if (fixed_black_shading[channel] != NULL) 11340 memset (fixed_black_shading[channel], 0, 0x7f8 * sizeof (USHORT)); 11341 else 11342 ret = ERROR; 11343 11344 /* Second table */ 11345 if (fixed_white_shading[channel] == NULL) 11346 fixed_white_shading[channel] = 11347 (USHORT *) malloc (0x7f8 * sizeof (USHORT)); 11348 11349 if (fixed_white_shading[channel] != NULL) 11350 memset (fixed_white_shading[channel], 0, 0x7f8 * sizeof (USHORT)); 11351 else 11352 ret = ERROR; 11353 11354 channel++; 11355 } 11356 11357 return ret; 11358} 11359 11360static SANE_Int 11361Calib_CreateBuffers (struct st_device *dev, struct st_calibration *buffer, 11362 SANE_Int my14b4) 11363{ 11364 SANE_Int ebp, ret, channel; 11365 11366 ret = ERROR; 11367 (void) dev; 11368 11369 buffer->shadinglength = scan.coord.width; 11370 ebp = 0x14; 11371 11372 if (my14b4 != 0) 11373 { 11374 /* 673d */ 11375 if (Calib_CreateFixedBuffers () == OK) 11376 { 11377 for (channel = 0; channel < 3; channel++) 11378 { 11379 buffer->white_shading[channel] = fixed_white_shading[channel]; 11380 buffer->black_shading[channel] = fixed_black_shading[channel]; 11381 } 11382 ret = OK; 11383 } 11384 } 11385 else 11386 { 11387 /* 677f */ 11388 SANE_Int pos; 11389 channel = 0; 11390 while ((channel < 3) && (ret == OK)) 11391 { 11392 buffer->black_shading[channel] = 11393 (USHORT *) malloc (ebp + 11394 (buffer->shadinglength * sizeof (USHORT))); 11395 buffer->white_shading[channel] = 11396 (USHORT *) malloc (ebp + 11397 (buffer->shadinglength * sizeof (USHORT))); 11398 if ((buffer->black_shading[channel] != NULL) 11399 && (buffer->white_shading[channel] != NULL)) 11400 { 11401 for (pos = 0; pos < buffer->shadinglength; pos++) 11402 { 11403 buffer->black_shading[channel][pos] = 0x00; 11404 buffer->white_shading[channel][pos] = 0x4000; 11405 } 11406 ret = OK; 11407 } 11408 else 11409 Calib_FreeBuffers (buffer); 11410 11411 channel++; 11412 } 11413 } 11414 11415 DBG (DBG_FNC, "> Calib_CreateBuffers: *buffer, my14b4=%i): %i\n", my14b4, 11416 ret); 11417 11418 return ret; 11419} 11420 11421static void 11422Calib_FreeBuffers (struct st_calibration *caltables) 11423{ 11424 DBG (DBG_FNC, "> Calib_FreeBuffers(*caltables)\n"); 11425 11426 if (caltables != NULL) 11427 { 11428 SANE_Int channel; 11429 11430 for (channel = 0; channel < 3; channel++) 11431 { 11432 if (caltables->black_shading[channel] != NULL) 11433 { 11434 free (caltables->black_shading[channel]); 11435 caltables->black_shading[channel] = NULL; 11436 } 11437 11438 if (caltables->white_shading[channel] != NULL) 11439 { 11440 free (caltables->white_shading[channel]); 11441 caltables->white_shading[channel] = NULL; 11442 } 11443 } 11444 } 11445} 11446 11447static SANE_Int 11448Calib_LoadConfig (struct st_device *dev, 11449 struct st_calibration_config *calibcfg, SANE_Int scantype, 11450 SANE_Int resolution, SANE_Int bitmode) 11451{ 11452 SANE_Int section, a; 11453 struct st_autoref refcfg; 11454 11455 DBG (DBG_FNC, 11456 "> Calib_LoadConfig(*calibcfg, scantype=%s, resolution=%i, bitmode=%i)\n", 11457 dbg_scantype (scantype), resolution, bitmode); 11458 11459 switch (scantype) 11460 { 11461 case ST_NEG: 11462 section = CALIBNEGATIVEFILM; 11463 break; 11464 case ST_TA: 11465 section = CALIBTRANSPARENT; 11466 break; 11467 default: 11468 section = CALIBREFLECTIVE; 11469 break; 11470 } 11471 11472 calibcfg->WStripXPos = get_value (section, WSTRIPXPOS, 0, FITCALIBRATE); 11473 calibcfg->WStripYPos = get_value (section, WSTRIPYPOS, 0, FITCALIBRATE); 11474 calibcfg->BStripXPos = get_value (section, BSTRIPXPOS, 0, FITCALIBRATE); 11475 calibcfg->BStripYPos = get_value (section, WSTRIPYPOS, 0, FITCALIBRATE); 11476 11477 /* get calibration wrefs */ 11478 cfg_wrefs_get (dev->sensorcfg->type, bitmode, resolution, scantype, 11479 &calibcfg->WRef[CL_RED], &calibcfg->WRef[CL_GREEN], 11480 &calibcfg->WRef[CL_BLUE]); 11481 11482 /* 4913 */ 11483 11484 for (a = CL_RED; a <= CL_BLUE; a++) 11485 { 11486 WRef[a] = _B0 (calibcfg->WRef[a]); 11487 11488 calibcfg->BRef[a] = get_value (section, BREFR + a, 10, FITCALIBRATE); 11489 calibcfg->OffsetEven1[a] = 11490 get_value (section, OFFSETEVEN1R + a, 256, FITCALIBRATE); 11491 calibcfg->OffsetEven2[a] = 11492 get_value (section, OFFSETEVEN2R + a, 0, FITCALIBRATE); 11493 calibcfg->OffsetOdd1[a] = 11494 get_value (section, OFFSETODD1R + a, 256, FITCALIBRATE); 11495 calibcfg->OffsetOdd2[a] = 11496 get_value (section, OFFSETODD2R + a, 0, FITCALIBRATE); 11497 } 11498 11499 calibcfg->RefBitDepth = 11500 _B0 (get_value (section, REFBITDEPTH, 8, FITCALIBRATE)); 11501 calibcfg->CalibOffset10n = 11502 _B0 (get_value (section, CALIBOFFSET10N, 3, FITCALIBRATE)); 11503 calibcfg->CalibOffset20n = 11504 _B0 (get_value (section, CALIBOFFSET20N, 0, FITCALIBRATE)); 11505 calibcfg->OffsetHeight = 11506 get_value (section, OFFSETHEIGHT, 10, FITCALIBRATE); 11507 11508 /* 4ae9 */ 11509 11510 /* get left coordinate and length to calibrate offset */ 11511 cfg_offset_get (dev->sensorcfg->type, resolution, scantype, 11512 &calibcfg->OffsetPixelStart, &calibcfg->OffsetNPixel); 11513 11514 /*4c49 */ 11515 calibcfg->OffsetNSigma = get_value (section, OFFSETNSIGMA, 2, FITCALIBRATE); 11516 calibcfg->OffsetTargetMax = 11517 get_value (section, OFFSETTARGETMAX, 0x32, FITCALIBRATE) * 0.01; 11518 calibcfg->OffsetTargetMin = 11519 get_value (section, OFFSETTARGETMIN, 2, FITCALIBRATE) * 0.01; 11520 calibcfg->OffsetBoundaryRatio1 = 11521 get_value (section, OFFSETBOUNDARYRATIO1, 0x64, FITCALIBRATE) * 0.01; 11522 calibcfg->OffsetBoundaryRatio2 = 11523 get_value (section, OFFSETBOUNDARYRATIO2, 0x64, FITCALIBRATE) * 0.01; 11524 11525 calibcfg->OffsetAvgRatio1 = 11526 get_value (section, OFFSETAVGRATIO1, 0x64, FITCALIBRATE) * 0.01; 11527 calibcfg->OffsetAvgRatio2 = 11528 get_value (section, OFFSETAVGRATIO2, 0x64, FITCALIBRATE) * 0.01; 11529 calibcfg->AdcOffQuickWay = 11530 get_value (section, ADCOFFQUICKWAY, 1, FITCALIBRATE); 11531 calibcfg->AdcOffPredictStart = 11532 get_value (section, ADCOFFPREDICTSTART, 0xc8, FITCALIBRATE); 11533 calibcfg->AdcOffPredictEnd = 11534 get_value (section, ADCOFFPREDICTEND, 0x1f4, FITCALIBRATE); 11535 calibcfg->AdcOffEvenOdd = 11536 get_value (section, ADCOFFEVENODD, 1, FITCALIBRATE); 11537 calibcfg->OffsetTuneStep1 = 11538 _B0 (get_value (section, OFFSETTUNESTEP1, 1, FITCALIBRATE)); 11539 calibcfg->OffsetTuneStep2 = 11540 _B0 (get_value (section, OFFSETTUNESTEP2, 1, FITCALIBRATE)); 11541 calibcfg->CalibGain10n = get_value (section, CALIBGAIN10N, 1, FITCALIBRATE); 11542 calibcfg->CalibGain20n = get_value (section, CALIBGAIN20N, 0, FITCALIBRATE); 11543 calibcfg->CalibPAGOn = get_value (section, CALIBPAGON, 0, FITCALIBRATE); 11544 11545 for (a = CL_RED; a <= CL_BLUE; a++) 11546 { 11547 calibcfg->OffsetAvgTarget[a] = 11548 _B0 (get_value (section, OFFSETAVGTARGETR + a, 0x0d, FITCALIBRATE)); 11549 calibcfg->PAG[a] = get_value (section, PAGR + a, 3, FITCALIBRATE); 11550 calibcfg->Gain1[a] = get_value (section, GAIN1R + a, 4, FITCALIBRATE); 11551 calibcfg->Gain2[a] = get_value (section, GAIN2R + a, 4, FITCALIBRATE); 11552 calibcfg->WShadingPreDiff[a] = 11553 get_value (section, WSHADINGPREDIFFR + a, -1, FITCALIBRATE); 11554 calibcfg->BShadingPreDiff[a] = 11555 get_value (section, BSHADINGPREDIFFR + a, 2, FITCALIBRATE); 11556 } 11557 11558 calibcfg->GainHeight = get_value (section, GAINHEIGHT, 0x1e, FITCALIBRATE); 11559 calibcfg->GainTargetFactor = 11560 get_value (section, GAINTARGETFACTOR, 0x5a, FITCALIBRATE) * 0.01; 11561 calibcfg->TotShading = get_value (section, TOTSHADING, 0, FITCALIBRATE); 11562 11563 /* White shading */ 11564 calibcfg->WShadingOn = get_value (section, WSHADINGON, 3, FITCALIBRATE); 11565 calibcfg->WShadingHeight = 11566 get_value (section, WSHADINGHEIGHT, 0x18, FITCALIBRATE); 11567 11568 /* Black shading */ 11569 calibcfg->BShadingOn = get_value (section, BSHADINGON, 2, FITCALIBRATE); 11570 calibcfg->BShadingHeight = 11571 get_value (section, BSHADINGHEIGHT, 0x1e, FITCALIBRATE); 11572 11573 calibcfg->BShadingDefCutOff = 11574 get_value (section, BSHADINGDEFCUTOFF, 0, FITCALIBRATE); 11575 11576 refcfg.extern_boundary = 0; 11577 cfg_autoref_get (&refcfg); 11578 calibcfg->ExternBoundary = refcfg.extern_boundary * 0.01; 11579 11580 calibcfg->EffectivePixel = 11581 cfg_effectivepixel_get (dev->sensorcfg->type, resolution); 11582 11583 return OK; 11584} 11585 11586static SANE_Int 11587Calib_AdcGain (struct st_device *dev, struct st_calibration_config *calibcfg, 11588 SANE_Int arg2, SANE_Int gaincontrol) 11589{ 11590 /* 11591 0606F8E0 04F60738 |Arg1 = 04F60738 11592 0606F8E4 0606F90C |Arg2 = 0606F90C calibcfg 11593 0606F8E8 00000001 |Arg3 = 00000001 arg2 11594 0606F8EC 00000001 \Arg4 = 00000001 gaincontrol 11595 */ 11596 11597 SANE_Int rst = ERROR; 11598 SANE_Byte *myRegs; /*f1c0 */ 11599 11600 DBG (DBG_FNC, "+ Calib_AdcGain(*calibcfg, arg2=%i, gaincontrol=%i)\n", arg2, 11601 gaincontrol); 11602 11603 myRegs = (SANE_Byte *) malloc (sizeof (SANE_Byte) * RT_BUFFER_LEN); 11604 if (myRegs != NULL) 11605 { 11606 struct st_scanparams *scancfg; /*f17c */ 11607 SANE_Int bytes_per_line, bytes_to_next_colour, bytes_per_pixel; 11608 11609 /* get register values to perform adc gain calibration */ 11610 memcpy (myRegs, &calibdata->Regs, sizeof (SANE_Byte) * RT_BUFFER_LEN); 11611 11612 scancfg = 11613 (struct st_scanparams *) malloc (sizeof (struct st_scanparams)); 11614 if (scancfg != NULL) 11615 { 11616 SANE_Byte *image, *pgain, *pcalgain; 11617 11618 /* get proper scan configuration */ 11619 memcpy (scancfg, &calibdata->scancfg, 11620 sizeof (struct st_scanparams)); 11621 11622 /* set gain control type */ 11623 Lamp_SetGainMode (dev, myRegs, scancfg->resolution_x, gaincontrol); 11624 11625 /* 8-bit depth */ 11626 scancfg->depth = 8; 11627 11628 /* set coordinates */ 11629 if ((scan.scantype > 0) && (scan.scantype < 4)) 11630 scancfg->coord.left += scan.ser; 11631 11632 if ((scancfg->coord.width & 1) == 0) 11633 scancfg->coord.width++; 11634 11635 scancfg->coord.top = 1; 11636 scancfg->coord.height = calibcfg->OffsetHeight; 11637 11638 /* three more values to read image data after getting image from scanner */ 11639 switch (scancfg->colormode) 11640 { 11641 case CM_GRAY: 11642 case CM_LINEART: 11643 bytes_to_next_colour = 0; 11644 bytes_per_pixel = 1; 11645 bytes_per_line = scancfg->coord.width; 11646 break; 11647 default: /* CM_COLOR */ 11648 /* c027 */ 11649 bytes_to_next_colour = 1; 11650 bytes_per_line = scancfg->coord.width * 3; 11651 if (scancfg->samplerate == LINE_RATE) 11652 { 11653 bytes_to_next_colour = scancfg->coord.width; 11654 bytes_per_pixel = 1; 11655 } 11656 else 11657 bytes_per_pixel = 3; 11658 break; 11659 } 11660 11661 /*7fc7 */ 11662 scancfg->v157c = bytes_per_line; 11663 scancfg->bytesperline = bytes_per_line; 11664 11665 /* select type of gain parameters to set */ 11666 if (arg2 != 0) 11667 { 11668 pgain = calibdata->gain_offset.vgag1; 11669 pcalgain = calibcfg->Gain1; 11670 } 11671 else 11672 { 11673 /*7ff2 */ 11674 pgain = calibdata->gain_offset.vgag2; 11675 pcalgain = calibcfg->Gain2; 11676 } 11677 11678 /*8002 */ 11679 /* Allocate space for image | size = 132912 */ 11680 image = 11681 (SANE_Byte *) malloc (sizeof (SANE_Byte) * 11682 ((scancfg->coord.height + 11683 16) * bytes_per_line)); 11684 if (image != NULL) 11685 { 11686 /* Lets read image */ 11687 if (RTS_GetImage 11688 (dev, myRegs, scancfg, &calibdata->gain_offset, image, NULL, 11689 OP_STATIC_HEAD, gaincontrol) == OK) 11690 { 11691 SANE_Int a; 11692 SANE_Int vmin[3], vmax[3]; 11693 double dval[3] = { 0.0 }; /*f1a8 f1b0 f1b8 */ 11694 SANE_Byte *pimage = image; 11695 11696 /* initialize values */ 11697 for (a = CL_RED; a <= CL_BLUE; a++) 11698 { 11699 calibcfg->unk1[a] = 0; 11700 calibcfg->unk2[a] = 0xff; 11701 11702 vmin[a] = 0xff; 11703 vmax[a] = 0; 11704 } 11705 11706 /* process image data */ 11707 if (scancfg->coord.width > 0) 11708 { 11709 /*8104 */ 11710 SANE_Int pos, myheight /*f164 */ ; 11711 SANE_Int chn_sum[3]; 11712 11713 for (pos = scancfg->coord.width; pos > 0; pos--) 11714 { 11715 chn_sum[CL_RED] = chn_sum[CL_GREEN] = 11716 chn_sum[CL_BLUE] = 0; 11717 11718 if (scancfg->coord.height > 0) 11719 for (myheight = 0; 11720 myheight < scancfg->coord.height; myheight++) 11721 for (a = CL_RED; a <= CL_BLUE; a++) 11722 chn_sum[a] += 11723 *(pimage + (bytes_per_line * myheight) + 11724 (bytes_to_next_colour * a)); 11725 11726 /*816e */ 11727 for (a = CL_RED; a <= CL_BLUE; a++) 11728 { 11729 vmin[a] = 11730 min (vmin[a], 11731 chn_sum[a] / scancfg->coord.height); 11732 vmax[a] = 11733 max (vmax[a], 11734 chn_sum[a] / scancfg->coord.height); 11735 11736 calibcfg->unk1[a] = 11737 max (calibcfg->unk1[a], vmax[a]); 11738 calibcfg->unk2[a] = 11739 min (calibcfg->unk1[a], vmin[a]); 11740 11741 dval[a] += vmax[a] & 0xffff; 11742 } 11743 11744 pimage += bytes_per_pixel; 11745 } 11746 } 11747 11748 /*82b0 */ 11749 dval[CL_RED] /= scancfg->coord.width; 11750 dval[CL_GREEN] /= scancfg->coord.width; 11751 dval[CL_BLUE] /= scancfg->coord.width; 11752 11753 DBG (DBG_FNC, " -> adcgain (av/l): r=%f, g=%f, b=%f\n", 11754 dval[CL_RED], dval[CL_GREEN], dval[CL_BLUE]); 11755 DBG (DBG_FNC, " -> (max ): R=%i, G=%i, B=%i\n", 11756 calibcfg->unk1[CL_RED], calibcfg->unk1[CL_GREEN], 11757 calibcfg->unk1[CL_BLUE]); 11758 DBG (DBG_FNC, " -> (min ): r=%i, g=%i, b=%i\n", 11759 calibcfg->unk2[CL_RED], calibcfg->unk2[CL_GREEN], 11760 calibcfg->unk2[CL_BLUE]); 11761 11762 if (scancfg->colormode == CM_COLOR) 11763 { 11764 /*8353 */ 11765 double dvalue; 11766 SANE_Int ival; 11767 11768 for (a = CL_RED; a <= CL_BLUE; a++) 11769 { 11770 dvalue = 11771 ((((calibcfg->WRef[a] * (1 << scancfg->depth)) * 11772 calibcfg->GainTargetFactor) * 0.00390625) / 11773 dval[a]) * ((44 - pgain[a]) / 40); 11774 if (dvalue > 0.9090909090909091) 11775 { 11776 /*83d7 */ 11777 dvalue = min (44 - (40 / dvalue), 31); 11778 ival = dvalue; 11779 pgain[a] = _B0 (ival); 11780 pcalgain[a] = _B0 (ival); 11781 } 11782 else 11783 { 11784 pgain[a] = 0; 11785 pcalgain[a] = 0; 11786 } 11787 } 11788 } 11789 else 11790 { 11791 /*843c */ 11792 /*falta codigo */ 11793 double dvalue; 11794 SANE_Int ival; 11795 11796 dvalue = 11797 ((44 - 11798 pgain[CL_RED]) / 40) * ((((1 << scancfg->depth) * 11799 calibcfg->WRef[scancfg-> 11800 channel]) * 11801 0.9) * 0.00390625) / 11802 17.08509389671362; 11803 11804 for (a = CL_RED; a <= CL_BLUE; a++) 11805 { 11806 if (dvalue > 0.9090909090909091) 11807 { 11808 dvalue = min (44 - (40 / dvalue), 31); 11809 ival = dvalue; 11810 pgain[a] = _B0 (ival); 11811 pcalgain[a] = _B0 (ival); 11812 } 11813 else 11814 { 11815 /*84e3 */ 11816 pgain[a] = 0; 11817 pcalgain[a] = 0; 11818 } 11819 } 11820 } 11821 11822 /*84fa */ 11823 /* Save buffer */ 11824 if (RTS_Debug->SaveCalibFile != FALSE) 11825 { 11826 dbg_tiff_save ("adcgain.tiff", 11827 scancfg->coord.width, 11828 scancfg->coord.height, 11829 scancfg->depth, 11830 CM_COLOR, 11831 scancfg->resolution_x, 11832 scancfg->resolution_y, 11833 image, 11834 (scancfg->coord.height + 11835 16) * bytes_per_line); 11836 } 11837 11838 /* check if peak values are above offset average target + 5 */ 11839 for (a = CL_RED; a <= CL_BLUE; a++) 11840 if (calibcfg->unk1[a] >= calibcfg->OffsetAvgTarget[a] + 5) 11841 { 11842 rst = OK; 11843 break; 11844 } 11845 } 11846 11847 free (image); 11848 } 11849 11850 free (scancfg); 11851 } 11852 11853 free (myRegs); 11854 } 11855 11856 /* v14b8 = (rst == OK)? 0: 1; */ 11857 11858 /* show */ 11859 dbg_calibtable (&calibdata->gain_offset); 11860 11861 DBG (DBG_FNC, "- Calib_AdcGain: %i\n", rst); 11862 11863 return rst; 11864} 11865 11866static SANE_Int 11867GainOffset_Save (struct st_device *dev, SANE_Int * offset, SANE_Byte * gain) 11868{ 11869 SANE_Int rst = OK; 11870 11871 DBG (DBG_FNC, "+ GainOffset_Save(*offset, *gain):\n"); 11872 11873 /* check if chipset supports accessing eeprom */ 11874 if ((dev->chipset->capabilities & CAP_EEPROM) != 0) 11875 { 11876 if ((offset != NULL) && (gain != NULL)) 11877 { 11878 SANE_Int a, crc, value; 11879 11880 crc = 0x5B; 11881 for (a = CL_RED; a <= CL_BLUE; a++) 11882 { 11883 value = (*gain << 9) | *offset; 11884 crc = _B0 (abs (crc - _B0 (value))); 11885 rst = 11886 RTS_EEPROM_WriteWord (dev->usb_handle, 0x70 + (a * 2), value); 11887 } 11888 11889 if (rst == OK) 11890 rst = RTS_EEPROM_WriteByte (dev->usb_handle, 0x76, crc); 11891 } 11892 else 11893 rst = ERROR; 11894 } 11895 11896 DBG (DBG_FNC, "- GainOffset_Save: %i\n", rst); 11897 11898 return rst; 11899} 11900 11901static SANE_Int 11902Calib_PAGain (struct st_device *dev, struct st_calibration_config *calibcfg, 11903 SANE_Int gainmode) 11904{ 11905 SANE_Byte *Regs; 11906 struct st_scanparams *scancfg; 11907 SANE_Int channel_size; 11908 SANE_Int bytes_to_next_colour = 0; 11909 SANE_Int bytes_per_pixel = 0; 11910 SANE_Int length = 0; 11911 SANE_Byte *image; 11912 double rst; 11913 SANE_Int ret = ERROR; 11914 11915 DBG (DBG_FNC, "+ Calib_PAGain(*calibcfg, gainmode=%i)\n", gainmode); 11916 11917 Regs = (SANE_Byte *) malloc (RT_BUFFER_LEN * sizeof (SANE_Byte)); 11918 if (Regs != NULL) 11919 { 11920 scancfg = 11921 (struct st_scanparams *) malloc (sizeof (struct st_scanparams)); 11922 if (scancfg != NULL) 11923 { 11924 memcpy (Regs, &calibdata->Regs, RT_BUFFER_LEN * sizeof (SANE_Byte)); 11925 memcpy (scancfg, &calibdata->scancfg, 11926 sizeof (struct st_scanparams)); 11927 11928 if (scan.scantype == ST_NORMAL) 11929 { 11930 /* bfa5 */ 11931 scancfg->coord.left = scan.ser; 11932 scancfg->coord.width = (scancfg->sensorresolution * 17) / 2; 11933 } 11934 else 11935 { 11936 scancfg->coord.left = scan.ser + v0750; 11937 scancfg->coord.width = (scancfg->sensorresolution * 3) / 2; 11938 } 11939 11940 /* bfca */ 11941 if ((scancfg->coord.width & 1) == 1) 11942 scancfg->coord.width++; 11943 11944 scancfg->coord.top = 1; 11945 scancfg->coord.height = calibcfg->OffsetHeight; 11946 11947 channel_size = (scancfg->depth > 8) ? 2 : 1; 11948 11949 switch (scancfg->colormode) 11950 { 11951 case CM_GRAY: 11952 case CM_LINEART: 11953 bytes_to_next_colour = 0; 11954 bytes_per_pixel = 1; 11955 length = channel_size * scancfg->coord.width; 11956 break; 11957 default: /* CM_COLOR */ 11958 /* c027 */ 11959 bytes_to_next_colour = 1; 11960 length = (channel_size * scancfg->coord.width) * 3; 11961 if (scancfg->samplerate == LINE_RATE) 11962 { 11963 bytes_to_next_colour = scancfg->coord.width; 11964 bytes_per_pixel = 1; 11965 } 11966 else 11967 bytes_per_pixel = 3; 11968 break; 11969 } 11970 11971 /* c070 */ 11972 scancfg->v157c = length; 11973 11974 image = 11975 (SANE_Byte *) malloc ((scancfg->coord.height * length) * 11976 sizeof (SANE_Byte)); 11977 if (image != NULL) 11978 { 11979 ret = 11980 RTS_GetImage (dev, Regs, scancfg, &calibdata->gain_offset, 11981 image, 0, OP_STATIC_HEAD, gainmode); 11982 if (ret == OK) 11983 { 11984 /* 429c105 */ 11985 SANE_Int a; 11986 SANE_Byte *ptr[3]; 11987 SANE_Int vmin[3] = { 255, 255, 255 }; /* f16c|f16e|f170 */ 11988 SANE_Int vmax[3] = { 0, 0, 0 }; /* f164|f166|f168 */ 11989 SANE_Int total[3]; 11990 11991 ptr[CL_RED] = image; 11992 ptr[CL_GREEN] = image + bytes_to_next_colour; 11993 ptr[CL_BLUE] = image + (bytes_to_next_colour * 2); 11994 11995 if (scancfg->coord.width > 0) 11996 { 11997 SANE_Int pos, b; 11998 11999 for (pos = 0; pos < scancfg->coord.width; pos++) 12000 { 12001 total[CL_BLUE] = 0; 12002 total[CL_GREEN] = 0; 12003 total[CL_RED] = 0; 12004 12005 for (a = 0; a < scancfg->coord.height; a++) 12006 { 12007 for (b = CL_RED; b <= CL_BLUE; b++) 12008 total[b] += 12009 *(ptr[b] + 12010 ((scancfg->coord.height - a) * length)); 12011 } 12012 12013 /* c1a5 */ 12014 for (a = CL_RED; a <= CL_BLUE; a++) 12015 { 12016 total[a] /= scancfg->coord.height; 12017 vmin[a] = min (vmin[a], total[a]); 12018 vmax[a] = max (vmax[a], total[a]); 12019 12020 ptr[a] += bytes_per_pixel; 12021 } 12022 } 12023 } 12024 12025 /* 429c234 */ 12026 for (a = CL_RED; a <= CL_BLUE; a++) 12027 { 12028 rst = 12029 (calibcfg->WRef[a] * calibcfg->GainTargetFactor) / 12030 vmax[a]; 12031 if (rst <= 1.5) 12032 { 12033 if (rst <= 1.286) 12034 { 12035 if (rst <= 1.125) 12036 calibdata->gain_offset.pag[a] = 0; 12037 else 12038 calibdata->gain_offset.pag[a] = 1; 12039 } 12040 else 12041 calibdata->gain_offset.pag[a] = 2; 12042 } 12043 else 12044 calibdata->gain_offset.pag[a] = 3; 12045 } 12046 } 12047 free (image); 12048 } 12049 free (scancfg); 12050 } 12051 free (Regs); 12052 } 12053 12054 DBG (DBG_FNC, "- Calib_PAGain: %i\n", ret); 12055 12056 return ret; 12057} 12058 12059static SANE_Int 12060Chipset_ID (struct st_device *dev) 12061{ 12062 SANE_Int ret; 12063 12064 if (Read_Word (dev->usb_handle, 0xfe3c, &ret) == OK) 12065 ret = _B0 (ret); 12066 else 12067 ret = 0; 12068 12069 DBG (DBG_FNC, "> Chipset_ID(): %i\n", ret); 12070 12071 return ret; 12072} 12073 12074static SANE_Int 12075Chipset_Name (struct st_device *dev, char *name, SANE_Int size) 12076{ 12077 SANE_Int rst = ERROR; 12078 12079 if (name != NULL) 12080 { 12081 strncpy (name, dev->chipset->name, size); 12082 rst = OK; 12083 } 12084 12085 return rst; 12086} 12087 12088static SANE_Int 12089Refs_Load (struct st_device *dev, SANE_Int * x, SANE_Int * y) 12090{ 12091 SANE_Int ret = OK; 12092 12093 DBG (DBG_FNC, "+ Refs_Load:\n"); 12094 12095 *y = *x = 0; 12096 12097 /* check if chipset supports accessing eeprom */ 12098 if ((dev->chipset->capabilities & CAP_EEPROM) != 0) 12099 { 12100 SANE_Int data; 12101 12102 ret = ERROR; 12103 12104 if (RTS_EEPROM_ReadWord (dev->usb_handle, 0x6a, &data) == OK) 12105 { 12106 *x = data; 12107 if (RTS_EEPROM_ReadWord (dev->usb_handle, 0x6c, &data) == OK) 12108 { 12109 *y = data; 12110 if (RTS_EEPROM_ReadWord (dev->usb_handle, 0x6e, &data) == OK) 12111 { 12112 if ((_B0 (*y + *x + data)) == 0x5a) 12113 ret = OK; 12114 } 12115 } 12116 } 12117 } 12118 12119 DBG (DBG_FNC, "- Refs_Load(y=%i, x=%i) : %i\n", *y, *x, ret); 12120 12121 return ret; 12122} 12123 12124static SANE_Int 12125Refs_Save (struct st_device *dev, SANE_Int left_leading, SANE_Int start_pos) 12126{ 12127 SANE_Int ret = OK; 12128 12129 DBG (DBG_FNC, "+ Refs_Save(left_leading=%i, start_pos=%i)\n", left_leading, 12130 start_pos); 12131 12132 /* check if chipset supports accessing eeprom */ 12133 if ((dev->chipset->capabilities & CAP_EEPROM) != 0) 12134 { 12135 ret = ERROR; 12136 12137 if (RTS_EEPROM_WriteWord (dev->usb_handle, 0x6a, left_leading) == OK) 12138 { 12139 if (RTS_EEPROM_WriteWord (dev->usb_handle, 0x6c, start_pos) == OK) 12140 { 12141 SANE_Byte data = _B0 (0x5a - (start_pos + left_leading)); 12142 ret = RTS_EEPROM_WriteByte (dev->usb_handle, 0x6e, data); 12143 } 12144 } 12145 } 12146 12147 DBG (DBG_FNC, "- Refs_Save: %i\n", ret); 12148 12149 return ret; 12150} 12151 12152static SANE_Int 12153Calib_AdcOffsetRT (struct st_device *dev, 12154 struct st_calibration_config *calibcfg, SANE_Int value) 12155{ 12156/* 1215705EFF8E4 04F10738 |Arg1 = 04F10738 1215805EFF8E8 05EFF90C |Arg2 = 05EFF90C calibcfg 1215905EFF8EC 00000001 \Arg3 = 00000001 value 12160*/ 12161 SANE_Byte Regs[RT_BUFFER_LEN]; /*f1c4 */ 12162 SANE_Int channels_per_dot; /*f108 */ 12163 struct st_scanparams scancfg; /*f18c */ 12164 SANE_Int *pedcg; /*f114 */ 12165 SANE_Int *podcg; /*f118 */ 12166 SANE_Int *poffseteven; /*f130 */ 12167 SANE_Int *poffsetodd; /*f128 */ 12168 SANE_Int channel; 12169 SANE_Int avgtarget[3]; /*f1b8 f1bc f1c0 */ 12170 SANE_Byte *scanbuffer; /*f0f8 */ 12171 SANE_Int scan_options; /*f12c */ 12172 SANE_Int highresolution; /*f144 */ 12173 double dbValues[3] = { 0, 0, 0 }; /*f148 f14c f150 */ 12174 SANE_Int do_loop; /*f0ec */ 12175 SANE_Int gainmode; 12176 SANE_Byte *ptr; /*f0f4 */ 12177 SANE_Byte *mvgag; /*f0e4 *//*f10c */ 12178 USHORT wvalues[9]; /*0856 0858 085a 085c 085e 0860 0862 0864 0866 */ 12179 SANE_Int imgcount = 0; 12180 /* myoffsetnpixel = f120 */ 12181 /* desp f0e8 & f140 */ 12182 12183 DBG (DBG_FNC, "+ Calib_AdcOffsetRT(*calibcfg, value=%i)\n", value); 12184 12185 memcpy (&Regs, &calibdata->Regs, RT_BUFFER_LEN * sizeof (SANE_Byte)); 12186 memcpy (&scancfg, &calibdata->scancfg, sizeof (struct st_scanparams)); 12187 12188 channels_per_dot = (calibdata->scancfg.colormode == CM_COLOR) ? 3 : 1; 12189 12190 if (value != 0) 12191 { 12192 pedcg = &calibdata->gain_offset.edcg1[CL_RED]; 12193 podcg = &calibdata->gain_offset.odcg1[CL_RED]; 12194 poffseteven = &calibcfg->OffsetEven1[CL_RED]; 12195 poffsetodd = &calibcfg->OffsetOdd1[CL_RED]; 12196 } 12197 else 12198 { 12199 /*c37c */ 12200 pedcg = &calibdata->gain_offset.edcg2[CL_RED]; 12201 podcg = &calibdata->gain_offset.odcg2[CL_RED]; 12202 poffseteven = &calibcfg->OffsetEven2[CL_RED]; 12203 poffsetodd = &calibcfg->OffsetOdd2[CL_RED]; 12204 } 12205 12206 /*c3a4 */ 12207 scancfg.coord.left = calibcfg->OffsetPixelStart; 12208 12209 if (channels_per_dot > 0) 12210 { 12211 for (channel = 0; channel < channels_per_dot; channel++) 12212 { 12213 avgtarget[channel] = calibcfg->OffsetAvgTarget[channel] << 8; 12214 if (avgtarget[channel] == 0) 12215 avgtarget[channel] = 0x80; 12216 } 12217 } 12218 12219 /* set image coordinates to scan */ 12220 scancfg.coord.width = calibcfg->OffsetNPixel; 12221 if ((scancfg.coord.width & 1) == 0) 12222 scancfg.coord.width++; 12223 12224 scancfg.bytesperline = channels_per_dot * scancfg.coord.width; 12225 scancfg.coord.top = 1; 12226 scancfg.coord.height = calibcfg->OffsetHeight; 12227 scancfg.depth = 8; 12228 12229 /* allocate memory to store image */ 12230 scanbuffer = 12231 (SANE_Byte *) malloc ((scancfg.bytesperline * calibcfg->OffsetHeight) * 12232 sizeof (SANE_Byte)); 12233 if (scanbuffer == NULL) 12234 return ERROR; 12235 12236 /*42ac477 */ 12237 scan_options = (linedarlampoff == 1) ? 1 : 0x101; 12238 highresolution = (scancfg.sensorresolution >= 1200) ? TRUE : FALSE; 12239 12240 do 12241 { 12242 if (channels_per_dot > 0) 12243 { 12244 for (channel = 0; channel < channels_per_dot; channel++) 12245 dbValues[channel] = 12246 (40 / (44 - calibdata->gain_offset.vgag2[channel])) * (40 / 12247 (44 - 12248 calibdata-> 12249 gain_offset. 12250 vgag1 12251 [channel])); 12252 } 12253 12254 /*429c50f */ 12255 /* Get Image */ 12256 gainmode = Lamp_GetGainMode (dev, scancfg.resolution_x, scan.scantype); 12257 if (RTS_GetImage 12258 (dev, Regs, &scancfg, &calibdata->gain_offset, scanbuffer, 0, 12259 scan_options, gainmode) != OK) 12260 { 12261 free (scanbuffer); 12262 return ERROR; 12263 } 12264 12265 /*429c55f */ 12266 /* Save retrieved image */ 12267 if (RTS_Debug->SaveCalibFile != FALSE) 12268 { 12269 char fname[30]; 12270 12271 imgcount++; 12272 if (snprintf (fname, 30, "adcoffset_rt%i.tiff", imgcount) > 0) 12273 dbg_tiff_save (fname, 12274 scancfg.coord.width, 12275 scancfg.coord.height, 12276 scancfg.depth, 12277 CM_COLOR, 12278 scancfg.resolution_x, 12279 scancfg.resolution_y, 12280 scanbuffer, 12281 scancfg.bytesperline * calibcfg->OffsetHeight); 12282 } 12283 12284 /*429c5a5 */ 12285 do_loop = FALSE; 12286 12287 if (highresolution == TRUE) 12288 { 12289 /* f0fc = f0e4 = channel */ 12290 SANE_Int lf104; 12291 SANE_Int *mydcg; /*f0f4 */ 12292 USHORT *mywvalue; /*ebp */ 12293 12294 SANE_Byte is_ready[6]; /*f174 f178 f17c f180 f184 f18c */ 12295 SANE_Byte *ptr_ready; /*f11c */ 12296 SANE_Int colour; 12297 12298 for (channel = 0; channel < 6; channel++) 12299 is_ready[channel] = FALSE; 12300 12301 if (channels_per_dot <= 0) 12302 break; 12303 12304 ptr = scanbuffer; 12305 mvgag = (SANE_Byte *) calibdata->gain_offset.vgag1; 12306 12307 for (channel = 0; channel < channels_per_dot; channel++) 12308 { 12309 for (lf104 = 0; lf104 < 2; lf104++) 12310 { 12311 if (lf104 == 0) 12312 { 12313 mywvalue = &wvalues[channel]; 12314 mydcg = pedcg; 12315 ptr_ready = &is_ready[0]; 12316 } 12317 else 12318 { 12319 /*1645 */ 12320 mywvalue = &wvalues[3]; 12321 mydcg = podcg; 12322 ptr_ready = &is_ready[3]; 12323 } 12324 12325 /*1658 */ 12326 if (ptr_ready[channel] == FALSE) 12327 { 12328 colour = 0; 12329 if (lf104 < calibcfg->OffsetNPixel) 12330 { 12331 SANE_Int dot; 12332 12333 for (dot = 0; 12334 dot < (calibcfg->OffsetNPixel - lf104 + 1) / 2; 12335 dot++) 12336 colour += 12337 scanbuffer[mvgag[(lf104 * channels_per_dot)] + 12338 (dot * (channels_per_dot * 2))]; 12339 } 12340 12341 /*c6b2 */ 12342 colour = colour << 8; 12343 if (colour == 0) 12344 { 12345 /*c6b9 */ 12346 if (mydcg[channel] != 0x1ff) 12347 { 12348 /*c6d5 */ 12349 mydcg[channel] = 0x1ff; 12350 do_loop = TRUE; 12351 } 12352 else 12353 ptr_ready[channel] = TRUE; 12354 } 12355 else 12356 { 12357 SANE_Int myesi; 12358 SANE_Int d; 12359 12360 /*c6e8 */ 12361 if (*mywvalue == 0) 12362 mywvalue += 2; 12363 12364 colour /= (calibcfg->OffsetNPixel / 2); 12365 if (colour >= avgtarget[channel]) 12366 { 12367 colour -= avgtarget[channel]; 12368 myesi = 0; 12369 } 12370 else 12371 { 12372 colour = avgtarget[channel] - colour; 12373 myesi = 1; 12374 } 12375 12376 d = mydcg[channel]; 12377 if (d < 0x100) 12378 d = 0xff - d; 12379 12380 if (myesi != 0) 12381 { 12382 /*c76e */ 12383 if ((d + colour) > 0x1ff) 12384 { 12385 if (*mvgag > 0) 12386 { 12387 *mvgag = *mvgag - 1; 12388 do_loop = TRUE; 12389 } 12390 else 12391 ptr_ready[channel] = TRUE; /*c7a0 */ 12392 } 12393 else 12394 d += colour; 12395 } 12396 else 12397 { 12398 /*c7ad */ 12399 if (colour > d) 12400 { 12401 if (*mvgag > 0) 12402 { 12403 *mvgag = *mvgag - 1; 12404 do_loop = TRUE; 12405 } 12406 else 12407 ptr_ready[channel] = TRUE; 12408 } 12409 else 12410 d -= colour; 12411 } 12412 12413 /*c7dd */ 12414 mydcg[channel] = (d < 0x100) ? 0x100 - d : d; 12415 } 12416 12417 dbg_calibtable (&calibdata->gain_offset); 12418 } 12419 } 12420 12421 /*c804 */ 12422 mvgag++; 12423 } 12424 } 12425 else 12426 { 12427 /* Low resolution */ 12428 12429 SANE_Byte is_ready[3]; 12430 SANE_Int colour; 12431 12432 /*429c845 */ 12433 for (channel = 0; channel < channels_per_dot; channel++) 12434 is_ready[channel] = FALSE; 12435 12436 if (channels_per_dot <= 0) 12437 break; 12438 12439 ptr = scanbuffer; 12440 mvgag = (SANE_Byte *) calibdata->gain_offset.vgag1; 12441 12442 for (channel = 0; channel < channels_per_dot; channel++) 12443 { 12444 if (is_ready[channel] == FALSE) 12445 { 12446 colour = 0; 12447 if (calibcfg->OffsetNPixel > 0) 12448 { 12449 SANE_Int dot; 12450 12451 /* Take one channel colour values from offsetnpixel pixels */ 12452 for (dot = 0; dot < calibcfg->OffsetNPixel; dot++) 12453 colour += *(ptr + (dot * channels_per_dot)); 12454 } 12455 12456 colour <<= 8; 12457 if (colour == 0) 12458 { 12459 if (pedcg[channel] != 0x1ff) 12460 { 12461 do_loop = TRUE; 12462 podcg[channel] = 0x1ff; 12463 pedcg[channel] = 0x1ff; 12464 } 12465 else 12466 is_ready[channel] = TRUE; 12467 } 12468 else 12469 { 12470 /*c8f7 */ 12471 SANE_Int myesi; 12472 SANE_Int op1, op2, op3; 12473 12474 /* Get colour average */ 12475 colour /= calibcfg->OffsetNPixel; 12476 12477 /* get absolute difference with avgtarget */ 12478 myesi = (colour > avgtarget[channel]) ? 0 : 1; 12479 colour = abs (avgtarget[channel] - colour); 12480 12481 if (scancfg.resolution_x > 600) 12482 { 12483 /*c923 */ 12484 if (wvalues[channel + 3] == 0) 12485 wvalues[channel + 3]++; 12486 12487 if (wvalues[channel] == 0) 12488 wvalues[channel]++; 12489 12490 op3 = max (wvalues[channel], wvalues[channel + 3]); 12491 } 12492 else 12493 { 12494 if (wvalues[channel + 6] == 0) 12495 wvalues[channel + 6]++; 12496 12497 op3 = wvalues[channel + 6]; 12498 } 12499 12500 /*c9d3 */ 12501 op1 = (SANE_Int) (colour / (dbValues[channel] * op3)); 12502 op2 = 12503 (pedcg[channel] < 12504 0x100) ? pedcg[channel] - 0xff : pedcg[channel]; 12505 12506 if (myesi != 0) 12507 { 12508 /*c9f5 */ 12509 if (((op2 + op1) & 0xffff) > 0x1ff) 12510 { 12511 if (*mvgag != 0) 12512 { 12513 do_loop = TRUE; 12514 *mvgag = *mvgag - 1; 12515 } 12516 else 12517 is_ready[channel] = TRUE; 12518 } 12519 else 12520 op2 += op1; 12521 } 12522 else 12523 { 12524 /*ca31 */ 12525 if (op1 > op2) 12526 { 12527 if (*mvgag > 0) 12528 { 12529 do_loop = TRUE; 12530 *mvgag = *mvgag - 1; 12531 } 12532 else 12533 is_ready[channel] = TRUE; 12534 } 12535 else 12536 op2 -= op1; 12537 } 12538 12539 /*ca54 */ 12540 if (op2 < 0x100) 12541 op2 = 0x100 - op2; 12542 12543 pedcg[channel] = op2; 12544 podcg[channel] = op2; 12545 } 12546 } 12547 /*ca6f */ 12548 ptr++; 12549 mvgag++; 12550 dbg_calibtable (&calibdata->gain_offset); 12551 } 12552 } 12553 } 12554 while (do_loop != FALSE); 12555 12556 /*429cad1 */ 12557 for (channel = 0; channel < 3; channel++) 12558 { 12559 poffseteven[channel] = 12560 (pedcg[channel] < 0x100) ? 0xff - pedcg[channel] : pedcg[channel]; 12561 poffsetodd[channel] = 12562 (podcg[channel] < 0x100) ? 0xff - podcg[channel] : podcg[channel]; 12563 } 12564 12565 free (scanbuffer); 12566 12567 return OK; 12568} 12569 12570static void 12571Calib_LoadCut (struct st_device *dev, struct st_scanparams *scancfg, 12572 SANE_Int scantype, struct st_calibration_config *calibcfg) 12573{ 12574 double mylong; /*ee78 */ 12575 double mylong2; 12576 /**/ SANE_Int channel[3]; 12577 SANE_Int a; 12578 12579 cfg_shading_cut_get (dev->sensorcfg->type, scancfg->depth, 12580 scancfg->resolution_x, scantype, &channel[0], 12581 &channel[1], &channel[2]); 12582 12583 mylong = 1 << scancfg->depth; 12584 12585 for (a = CL_RED; a <= CL_BLUE; a++) 12586 { 12587 mylong2 = channel[a]; 12588 calibcfg->ShadingCut[a] = (mylong * mylong2) * 0.000390625; 12589 } 12590} 12591 12592static SANE_Int 12593Calib_BWShading (struct st_calibration_config *calibcfg, 12594 struct st_calibration *myCalib, SANE_Int gainmode) 12595{ 12596 /* 12597 0603F8E4 0603F90C |Arg1 = 0603F90C calibcfg 12598 0603F8E8 0603FAAC |Arg2 = 0603FAAC myCalib 12599 0603F8EC 00000001 \Arg3 = 00000001 gainmode 12600 */ 12601 12602 /*falta codigo */ 12603 12604 /*silence gcc */ 12605 (void) calibcfg; 12606 (void) myCalib; 12607 (void) gainmode; 12608 12609 return OK; 12610} 12611 12612static SANE_Int 12613Calib_WhiteShading_3 (struct st_device *dev, 12614 struct st_calibration_config *calibcfg, 12615 struct st_calibration *myCalib, SANE_Int gainmode) 12616{ 12617/* 1261805EDF8E0 04F00738 |Arg1 = 04F00738 1261905EDF8E4 05EDF90C |Arg2 = 05EDF90C calibcfg 1262005EDF8E8 05EDFAAC |Arg3 = 05EDFAAC myCalib 1262105EDF8EC 00000001 \Arg4 = 00000001 gainmode 12622*/ 12623 SANE_Byte *myRegs; /*f1bc */ 12624 struct st_scanparams scancfg; /*f170 */ 12625 SANE_Int myWidth; /*f14c */ 12626 SANE_Int lf168, bytes_per_pixel; 12627 SANE_Int bytes_per_line; 12628 /**/ SANE_Int a; 12629 double lf1a4[3]; 12630 SANE_Int otherheight; /*f150 */ 12631 SANE_Int otherheight2; 12632 SANE_Int lf12c; 12633 SANE_Int lf130; 12634 double *buffer1; /*f138 */ 12635 double *buffer2; /*f144 */ 12636 SANE_Byte *scanbuffer; /*f164 */ 12637 SANE_Byte *ptr; /*f148 */ 12638 SANE_Int position; /*f140 */ 12639 SANE_Int lf13c, myHeight; 12640 SANE_Int myESI, myEDI; 12641 SANE_Int channel; /*f134 */ 12642 double myst; 12643 double sumatorio; 12644 SANE_Int rst; 12645 12646 DBG (DBG_FNC, "> Calib_WhiteShading3(*calibcfg, *myCalib, gainmode=%i)\n", 12647 gainmode); 12648 12649 myRegs = (SANE_Byte *) malloc (RT_BUFFER_LEN * sizeof (SANE_Byte)); 12650 memcpy (myRegs, &calibdata->Regs, RT_BUFFER_LEN * sizeof (SANE_Byte)); 12651 memcpy (&scancfg, &calibdata->scancfg, sizeof (struct st_scanparams)); 12652 12653 Lamp_SetGainMode (dev, myRegs, scancfg.resolution_x, gainmode); 12654 12655 rst = OK; 12656 scancfg.resolution_y = 200; 12657 switch (scan.scantype) 12658 { 12659 case ST_NORMAL: 12660 /*a184 */ 12661 scancfg.coord.left += scan.ser; 12662 scancfg.coord.width &= 0xffff; 12663 break; 12664 case ST_TA: 12665 case ST_NEG: 12666 scancfg.coord.left += scan.ser; 12667 break; 12668 } 12669 12670 /*a11b */ 12671 if ((scancfg.coord.width & 1) != 0) 12672 scancfg.coord.width++; 12673 12674 scancfg.coord.top = 1; 12675 scancfg.coord.height = calibcfg->WShadingHeight; 12676 12677 switch (scancfg.colormode) 12678 { 12679 case CM_GRAY: 12680 case CM_LINEART: 12681 myWidth = scancfg.coord.width; 12682 lf168 = 0; 12683 bytes_per_line = ((scancfg.depth + 7) / 8) * myWidth; 12684 bytes_per_pixel = 1; 12685 break; 12686 default: /* CM_COLOR */ 12687 myWidth = scancfg.coord.width * 3; 12688 bytes_per_line = ((scancfg.depth + 7) / 8) * myWidth; 12689 lf168 = (scancfg.samplerate == LINE_RATE) ? scancfg.coord.width : 1; 12690 bytes_per_pixel = (scancfg.samplerate == PIXEL_RATE) ? 3 : 1; 12691 break; 12692 } 12693 12694 /*a1e8 */ 12695 scancfg.v157c = bytes_per_line; 12696 scancfg.bytesperline = bytes_per_line; 12697 12698 for (a = 0; a < 3; a++) 12699 lf1a4[a] = (calibcfg->WRef[a] * (1 << scancfg.depth)) >> 8; 12700 12701 /* debug this code because if it's correct, lf130 and lf12c are always 2 */ 12702 otherheight = calibcfg->WShadingHeight - 3; 12703 otherheight -= (otherheight - 4); 12704 otherheight2 = otherheight / 2; 12705 otherheight -= otherheight2; 12706 lf130 = otherheight2; 12707 lf12c = otherheight; 12708 12709 buffer1 = (double *) malloc (otherheight * sizeof (double)); 12710 if (buffer1 == NULL) 12711 return ERROR; 12712 12713 buffer2 = (double *) malloc (otherheight * sizeof (double)); 12714 if (buffer2 == NULL) 12715 { 12716 free (buffer1); 12717 return ERROR; 12718 } 12719 12720 scanbuffer = 12721 (SANE_Byte *) malloc (((scancfg.coord.height + 16) * bytes_per_line) * 12722 sizeof (SANE_Byte)); 12723 if (scanbuffer == NULL) 12724 { 12725 free (buffer1); 12726 free (buffer2); 12727 return ERROR; 12728 } 12729 12730 /* Scan image */ 12731 myCalib->shading_enabled = FALSE; 12732 rst = 12733 RTS_GetImage (dev, myRegs, &scancfg, &calibdata->gain_offset, scanbuffer, 12734 myCalib, 0x20000080, gainmode); 12735 12736 for (a = 0; a < 3; a++) 12737 myCalib->WRef[a] *= ((1 << scancfg.depth) >> 8); 12738 12739 if (rst == ERROR) 12740 { 12741 free (buffer1); 12742 free (buffer2); 12743 free (scanbuffer); 12744 return ERROR; 12745 } 12746 12747 if (scancfg.depth > 8) 12748 { 12749 /*a6d9 */ 12750 position = 0; 12751 sumatorio = 0; 12752 if (myWidth > 0) 12753 { 12754 do 12755 { 12756 switch (scancfg.colormode) 12757 { 12758 case CM_GRAY: 12759 case CM_LINEART: 12760 channel = 0; 12761 lf13c = position; 12762 break; 12763 default: /*CM_COLOR */ 12764 if (scancfg.samplerate == PIXEL_RATE) 12765 { 12766 /* pixel rate */ 12767 channel = position % bytes_per_pixel; 12768 lf13c = position / bytes_per_pixel; 12769 } 12770 else 12771 { 12772 /* line rate */ 12773 channel = position / lf168; 12774 lf13c = position % lf168; 12775 } 12776 break; 12777 } 12778 12779 /*a743 */ 12780 if (lf130 > 0) 12781 memset (buffer1, 0, lf130 * sizeof (double)); 12782 12783 /*a761 */ 12784 if (lf12c > 0) 12785 { 12786 for (a = 0; a < lf12c; a++) 12787 buffer2[a] = (1 << scancfg.depth) - 1.0; 12788 } 12789 12790 /*a78f */ 12791 myESI = 0; 12792 myEDI = 0; 12793 ptr = scanbuffer + (position * 2); 12794 myHeight = 0; 12795 12796 if (otherheight > 0) 12797 { 12798 do 12799 { 12800 myst = 0; 12801 for (a = 0; a < 4; a++) 12802 myst += data_lsb_get (ptr + (a * (myWidth * 2)), 2); 12803 12804 myEDI = 0; 12805 myst = myst * 0.25; 12806 if (myHeight < (otherheight - 4)) 12807 { 12808 if (myst < buffer2[myESI]) 12809 { 12810 buffer2[myESI] = myst; 12811 if (lf12c > 0) 12812 { 12813 for (a = 0; a < lf12c; a++) 12814 if (buffer2[myESI] < buffer2[a]) 12815 myESI = a; 12816 } 12817 } 12818 12819 /*a820 */ 12820 if (myst >= buffer1[myEDI]) 12821 { 12822 buffer1[myEDI] = myst; 12823 if (lf130 > 0) 12824 { 12825 for (a = 0; a < lf130; a++) 12826 if (buffer1[myEDI] >= buffer1[a]) 12827 myEDI = a; 12828 } 12829 } 12830 sumatorio += myst; 12831 } 12832 else 12833 { 12834 /*a853 */ 12835 if (myHeight == (otherheight - 4)) 12836 { 12837 if (lf12c > 0) 12838 { 12839 for (a = 0; a < lf12c; a++) 12840 if (buffer2[myESI] >= buffer2[a]) 12841 myESI = a; 12842 } 12843 12844 if (lf130 > 0) 12845 { 12846 for (a = 0; a < lf130; a++) 12847 if (buffer1[myEDI] < buffer1[a]) 12848 myEDI = a; 12849 } 12850 } 12851 12852 /*a895 */ 12853 if (myst >= buffer2[myESI]) 12854 { 12855 /*a89c */ 12856 sumatorio -= buffer2[myESI]; 12857 sumatorio += myst; 12858 buffer2[myESI] = myst; 12859 if (lf12c > 0) 12860 { 12861 for (a = 0; a < lf12c; a++) 12862 if (buffer2[myESI] >= buffer2[a]) 12863 myESI = a; 12864 } 12865 } 12866 else 12867 { 12868 if (myst < buffer1[myEDI]) 12869 { 12870 sumatorio -= buffer1[myEDI]; 12871 sumatorio += myst; 12872 buffer1[myEDI] = myst; 12873 12874 if (lf130 > 0) 12875 { 12876 for (a = 0; a < lf130; a++) 12877 if (buffer1[myEDI] < buffer1[a]) 12878 myEDI = a; 12879 } 12880 } 12881 } 12882 } 12883 12884 /*a901 */ 12885 ptr += (myWidth * 2); 12886 myHeight++; 12887 } 12888 while (myHeight < otherheight); 12889 } 12890 12891 /*a924 */ 12892 scancfg.ser = 0; 12893 scancfg.startpos = otherheight - 4; 12894 12895 sumatorio = sumatorio / scancfg.startpos; 12896 if (myCalib->shading_enabled != FALSE) 12897 { 12898 /*a94a */ 12899 myCalib->white_shading[channel][lf13c] = 12900 (unsigned short) sumatorio; 12901 } 12902 else 12903 { 12904 /*a967 */ 12905 if ((scancfg.colormode != CM_GRAY) 12906 && (scancfg.colormode != CM_LINEART)) 12907 sumatorio /= lf1a4[channel]; 12908 else 12909 sumatorio /= lf1a4[scancfg.channel]; 12910 12911 sumatorio = min (sumatorio * 0x4000, 65535); 12912 12913 if (myRegs[0x1bf] != 0x18) 12914 myCalib->black_shading[channel][lf13c] |= 12915 (0x140 - 12916 ((((myRegs[0x1bf] >> 3) & 3) * 12917 3) << 6)) & ((int) sumatorio); 12918 else 12919 myCalib->white_shading[channel][lf13c] = 12920 (unsigned short) sumatorio; 12921 } 12922 12923 /*a9fd */ 12924 position++; 12925 } 12926 while (position < myWidth); 12927 } 12928 } 12929 else 12930 { 12931 /*a6d9 */ 12932 position = 0; 12933 sumatorio = 0; 12934 if (myWidth > 0) 12935 { 12936 do 12937 { 12938 switch (scancfg.colormode) 12939 { 12940 case CM_GRAY: 12941 case CM_LINEART: 12942 channel = 0; 12943 lf13c = position; 12944 break; 12945 default: /*CM_COLOR */ 12946 if (scancfg.samplerate == PIXEL_RATE) 12947 { 12948 channel = position % bytes_per_pixel; 12949 lf13c = position / bytes_per_pixel; 12950 } 12951 else 12952 { 12953 channel = position / lf168; 12954 lf13c = position % lf168; 12955 } 12956 break; 12957 } 12958 12959 /*a743 */ 12960 if (lf130 > 0) 12961 memset (buffer1, 0, lf130 * sizeof (double)); 12962 12963 /*a761 */ 12964 if (lf12c > 0) 12965 { 12966 for (a = 0; a < lf12c; a++) 12967 buffer2[a] = (1 << scancfg.depth) - 1.0; 12968 } 12969 12970 /*a78f */ 12971 myESI = 0; 12972 myEDI = 0; 12973 ptr = scanbuffer + position; 12974 myHeight = 0; 12975 12976 if (otherheight > 0) 12977 { 12978 do 12979 { 12980 myst = 0; 12981 for (a = 0; a < 4; a++) 12982 myst += *(ptr + (a * myWidth)); 12983 12984 myEDI = 0; 12985 myst *= 0.25; 12986 if (myHeight < (otherheight - 4)) 12987 { 12988 if (myst < buffer2[myESI]) 12989 { 12990 buffer2[myESI] = myst; 12991 if (lf12c > 0) 12992 { 12993 for (a = 0; a < lf12c; a++) 12994 if (buffer2[myESI] < buffer2[a]) 12995 myESI = a; 12996 } 12997 } 12998 /*a820 */ 12999 if (myst >= buffer1[myEDI]) 13000 { 13001 buffer1[myEDI] = myst; 13002 if (lf130 > 0) 13003 { 13004 for (a = 0; a < lf130; a++) 13005 if (buffer1[myEDI] >= buffer1[a]) 13006 myEDI = a; 13007 } 13008 } 13009 sumatorio += myst; 13010 } 13011 else 13012 { 13013 /*a853 */ 13014 if (myHeight == (otherheight - 4)) 13015 { 13016 if (lf12c > 0) 13017 { 13018 for (a = 0; a < lf12c; a++) 13019 if (buffer2[myESI] >= buffer2[a]) 13020 myESI = a; 13021 } 13022 13023 if (lf130 > 0) 13024 { 13025 for (a = 0; a < lf130; a++) 13026 if (buffer1[myEDI] < buffer1[a]) 13027 myEDI = a; 13028 } 13029 } 13030 13031 /*a895 */ 13032 if (myst >= buffer2[myESI]) 13033 { 13034 /*a89c */ 13035 sumatorio -= buffer2[myESI]; 13036 sumatorio += myst; 13037 buffer2[myESI] = myst; 13038 if (lf12c > 0) 13039 { 13040 for (a = 0; a < lf12c; a++) 13041 if (buffer2[myESI] >= buffer2[a]) 13042 myESI = a; 13043 } 13044 } 13045 else 13046 { 13047 if (myst < buffer1[myEDI]) 13048 { 13049 sumatorio -= buffer1[myEDI]; 13050 sumatorio += myst; 13051 buffer1[myEDI] = myst; 13052 13053 if (lf130 > 0) 13054 { 13055 for (a = 0; a < lf130; a++) 13056 if (buffer1[myEDI] < buffer1[a]) 13057 myEDI = a; 13058 } 13059 } 13060 } 13061 } 13062 /*a901 */ 13063 ptr += myWidth; 13064 myHeight++; 13065 } 13066 while (myHeight < otherheight); 13067 } 13068 /*a924 */ 13069 scancfg.ser = 0; 13070 scancfg.startpos = otherheight - 4; 13071 13072 sumatorio /= scancfg.startpos; 13073 if (myCalib->shading_enabled != FALSE) 13074 { 13075 /*a94a */ 13076 myCalib->white_shading[channel][lf13c] = 13077 (unsigned short) sumatorio; 13078 } 13079 else 13080 { 13081 /*a967 */ 13082 if ((scancfg.colormode != CM_GRAY) 13083 && (scancfg.colormode != CM_LINEART)) 13084 sumatorio /= lf1a4[channel]; 13085 else 13086 sumatorio /= lf1a4[scancfg.channel]; 13087 13088 sumatorio = min (sumatorio * 0x4000, 65535); 13089 13090 if (myRegs[0x1bf] != 0x18) 13091 myCalib->black_shading[channel][lf13c] |= 13092 (0x140 - 13093 ((((myRegs[0x1bf] >> 3) & 0x03) * 13094 3) << 6)) & ((int) sumatorio); 13095 else 13096 myCalib->white_shading[channel][lf13c] = 13097 (unsigned short) sumatorio; 13098 } 13099 /*a9fd */ 13100 position++; 13101 } 13102 while (position < myWidth); 13103 } 13104 } 13105 13106 /*aa12 */ 13107 if (RTS_Debug->SaveCalibFile != FALSE) 13108 { 13109 dbg_tiff_save ("whiteshading3.tiff", 13110 scancfg.coord.width, 13111 scancfg.coord.height, 13112 scancfg.depth, 13113 CM_COLOR, 13114 scancfg.resolution_x, 13115 scancfg.resolution_y, 13116 scanbuffer, 13117 (scancfg.coord.height + 16) * bytes_per_line); 13118 } 13119 13120 free (buffer1); 13121 free (buffer2); 13122 free (scanbuffer); 13123 13124 return OK; 13125} 13126 13127static SANE_Int 13128Calib_BlackShading (struct st_device *dev, 13129 struct st_calibration_config *calibcfg, 13130 struct st_calibration *myCalib, SANE_Int gainmode) 13131{ 13132 /* 13133 gainmode f8ec 13134 myCalib f8e8 13135 calibcfg f8e4 13136 */ 13137 SANE_Byte *myRegs; /*f1bc */ 13138 struct st_scanparams scancfg; /*f020 */ 13139 double shadingprediff[6]; /*f08c f094 f09c f0a4 f0ac f0b4 */ 13140 double mylong; /*f018 */ 13141 double maxvalue; /*eff8 */ 13142 double sumatorio = 0.0; 13143 double myst; 13144 SANE_Int rst; 13145 SANE_Int a; 13146 SANE_Int mheight; /*efe0 */ 13147 SANE_Int current_line; /*efe4 */ 13148 SANE_Int bytes_per_line; /*efd8 */ 13149 SANE_Int position; /*lefcc */ 13150 SANE_Int leff0, lf010, lefd0; 13151 SANE_Byte *buffer; /*efd4 */ 13152 SANE_Byte buff2[256]; /*F0BC */ 13153 SANE_Int buff3[0x8000]; 13154 SANE_Byte *ptr; /*f008 */ 13155 SANE_Int my14b4; /*f008 pisa ptr */ 13156 SANE_Int biggest; /*bx */ 13157 SANE_Int lowest; /*dx */ 13158 SANE_Int lefdc; 13159 SANE_Int channel; 13160 SANE_Int smvalues[3]; /*f04c f04e f050 */ 13161 double dbvalue[6]; /*lf05c lf060, lf064 lf068, lf06c lf070, 13162 lf074 lf078, lf07c lf080, lf084 lf088 */ 13163 13164 DBG (DBG_FNC, "> Calib_BlackShading(*calibcfg, *myCalib, gainmode=%i)\n", 13165 gainmode); 13166 13167 rst = OK; 13168 myRegs = (SANE_Byte *) malloc (RT_BUFFER_LEN * sizeof (SANE_Byte)); 13169 memcpy (myRegs, &calibdata->Regs, RT_BUFFER_LEN * sizeof (SANE_Byte)); 13170 memcpy (&scancfg, &calibdata->scancfg, sizeof (struct st_scanparams)); 13171 13172 Lamp_SetGainMode (dev, myRegs, scancfg.resolution_x, gainmode); 13173 13174 for (a = CL_RED; a <= CL_BLUE; a++) 13175 shadingprediff[a + 3] = calibcfg->BShadingPreDiff[a]; 13176 13177 if ((scan.scantype >= ST_NORMAL) && (scan.scantype <= ST_NEG)) 13178 scancfg.coord.left += scan.ser; 13179 13180 if ((scancfg.coord.width & 1) != 0) 13181 scancfg.coord.width++; 13182 13183 scancfg.coord.top = 1; 13184 scancfg.depth = 8; 13185 scancfg.coord.height = calibcfg->BShadingHeight; 13186 13187 if (scancfg.colormode != CM_COLOR) 13188 { 13189 bytes_per_line = scancfg.coord.width; 13190 leff0 = 0; 13191 lf010 = 1; 13192 } 13193 else 13194 { 13195 /*876c */ 13196 bytes_per_line = scancfg.coord.width * 3; 13197 if (scancfg.samplerate == LINE_RATE) 13198 { 13199 leff0 = scancfg.coord.width; 13200 lf010 = 1; 13201 } 13202 else 13203 { 13204 leff0 = 1; 13205 lf010 = 3; 13206 } 13207 } 13208 13209 scancfg.v157c = bytes_per_line; 13210 scancfg.bytesperline = bytes_per_line; 13211 13212 mylong = 1 << (16 - scancfg.depth); 13213 if ((myRegs[0x1bf] & 0x18) != 0) 13214 mylong /= 1 << (((myRegs[0x1bf] >> 5) & 3) + 4); 13215 13216 lefd0 = 13217 ((((myRegs[0x1bf] >> 3) & 2) << 8) - 13218 ((((myRegs[0x1bf] >> 3) & 1) * 3) << 6)) - 1; 13219 13220 if (scancfg.depth >= 8) 13221 maxvalue = ((1 << (scancfg.depth - 8)) << 8) - 1; 13222 else 13223 maxvalue = (256 / (1 << (8 - scancfg.depth))) - 1; 13224 13225 Calib_LoadCut (dev, &scancfg, scan.scantype, calibcfg); 13226 for (a = CL_RED; a <= CL_BLUE; a++) 13227 shadingprediff[a] = calibcfg->ShadingCut[a]; 13228 13229 if (calibcfg->BShadingOn == -1) 13230 { 13231 SANE_Int b, d; 13232 double e; 13233 13234 for (a = CL_RED; a <= CL_BLUE; a++) 13235 { 13236 myst = max (shadingprediff[a], 0); 13237 myst = (maxvalue >= myst) ? shadingprediff[a] : maxvalue; 13238 shadingprediff[a] = max (myst, 0); 13239 } 13240 13241 b = 0; 13242 13243 while (b < bytes_per_line) 13244 { 13245 if (scancfg.colormode != CM_COLOR) 13246 { 13247 channel = 0; 13248 d = b; 13249 } 13250 else 13251 { 13252 if (scancfg.samplerate == PIXEL_RATE) 13253 { 13254 channel = (b % lf010) & 0xffff; 13255 d = (b / lf010) & 0xffff; 13256 } 13257 else 13258 { 13259 channel = (b / leff0) & 0xffff; 13260 d = (b % leff0) & 0xffff; 13261 } 13262 } 13263 /*89d0 */ 13264 e = min (lefd0, mylong * shadingprediff[channel]); 13265 myCalib->black_shading[channel][d] |= (unsigned short) e & 0xffff; 13266 b++; 13267 } 13268 13269 return OK; 13270 } 13271 13272 /* Allocate buffer to read image */ 13273 mheight = scancfg.coord.height; 13274 buffer = 13275 (SANE_Byte *) malloc (((scancfg.coord.height + 16) * bytes_per_line) * 13276 sizeof (SANE_Byte)); 13277 if (buffer == NULL) 13278 return ERROR; 13279 13280 /* Turn off lamp */ 13281 Lamp_Status_Set (dev, NULL, FALSE, FLB_LAMP); 13282 usleep (200 * 1000); 13283 13284 /* Scan image */ 13285 myCalib->shading_enabled = FALSE; 13286 rst = 13287 RTS_GetImage (dev, myRegs, &scancfg, &calibdata->gain_offset, buffer, 13288 myCalib, 0x101, gainmode); 13289 if (rst == ERROR) 13290 { 13291 /*8ac2 */ 13292 free (buffer); 13293 memcpy (&calibdata->Regs, myRegs, RT_BUFFER_LEN * sizeof (SANE_Byte)); 13294 free (myRegs); 13295 return ERROR; 13296 } 13297 13298 /* myRegs isn't going to be used anymore */ 13299 free (myRegs); 13300 myRegs = NULL; 13301 13302 /* Turn on lamp again */ 13303 if (scan.scantype != ST_NORMAL) 13304 { 13305 Lamp_Status_Set (dev, NULL, FALSE, TMA_LAMP); 13306 usleep (1000 * 1000); 13307 } 13308 else 13309 Lamp_Status_Set (dev, NULL, TRUE, FLB_LAMP); 13310 13311 /* Save buffer */ 13312 if (RTS_Debug->SaveCalibFile != FALSE) 13313 { 13314 dbg_tiff_save ("blackshading.tiff", 13315 scancfg.coord.width, 13316 scancfg.coord.height, 13317 scancfg.depth, 13318 CM_COLOR, 13319 scancfg.resolution_x, 13320 scancfg.resolution_y, 13321 buffer, (scancfg.coord.height + 16) * bytes_per_line); 13322 } 13323 13324 if (scancfg.depth > 8) 13325 { 13326 /*8bb2 */ 13327 memset (&dbvalue, 0, 6 * sizeof (double)); 13328 position = 0; 13329 13330 if (bytes_per_line > 0) 13331 { 13332 do 13333 { 13334 memset (&buff3, 0, 0x8000 * sizeof (SANE_Int)); 13335 sumatorio = 0; 13336 ptr = buffer + position; 13337 current_line = 0; 13338 biggest = 0; 13339 lowest = (int) maxvalue; 13340 /* Toma los valores de una columna */ 13341 if (mheight > 0) 13342 { 13343 SANE_Int value; 13344 do 13345 { 13346 value = data_lsb_get (ptr, 2); 13347 biggest = max (biggest, value); 13348 if (current_line < mheight) 13349 { 13350 sumatorio += value; 13351 lowest = min (lowest, value); 13352 biggest = max (biggest, value); 13353 13354 buff3[value]++; 13355 } 13356 else 13357 { 13358 /*8cab */ 13359 if (value > lowest) 13360 { 13361 buff3[lowest]--; 13362 buff3[value]++; 13363 sumatorio += value; 13364 sumatorio -= lowest; 13365 13366 if (buff3[lowest] != 0) 13367 { 13368 do 13369 { 13370 lowest++; 13371 } 13372 while (buff3[lowest] == 0); 13373 } 13374 } 13375 } 13376 /*8d0b */ 13377 ptr += (bytes_per_line * 2); 13378 current_line++; 13379 } 13380 while (current_line < mheight); 13381 } 13382 /*8d27 */ 13383 sumatorio /= mheight; 13384 13385 if (scancfg.colormode != CM_COLOR) 13386 { 13387 channel = 0; 13388 lefdc = position; 13389 } 13390 else 13391 { 13392 /*8d5f */ 13393 if (scancfg.samplerate == PIXEL_RATE) 13394 { 13395 channel = position % lf010; 13396 lefdc = (position / lf010) & 0xffff; 13397 } 13398 else 13399 { 13400 channel = position / leff0; 13401 lefdc = position % leff0; 13402 } 13403 } 13404 13405 dbvalue[channel] += sumatorio; 13406 if ((scancfg.colormode == CM_GRAY) 13407 || (scancfg.colormode == CM_LINEART)) 13408 sumatorio += shadingprediff[scancfg.channel]; 13409 else 13410 sumatorio += shadingprediff[channel]; 13411 13412 myst = min (max (0, sumatorio), maxvalue); 13413 13414 dbvalue[channel + 3] = myst; 13415 13416 if ((calibcfg->BShadingOn == 1) || (calibcfg->BShadingOn == 2)) 13417 { 13418 if (calibcfg->BShadingOn == 2) 13419 { 13420 myst -= 13421 calibcfg->BRef[channel] * (1 << (scancfg.depth - 8)); 13422 myst = max (myst, 0); 13423 } 13424 /*8e6d */ 13425 myst *= mylong; 13426 myCalib->black_shading[channel][lefdc] = min (myst, lefd0); 13427 } 13428 13429 position++; 13430 } 13431 while (position < bytes_per_line); 13432 } 13433 } 13434 else 13435 { 13436 /*8eb6 */ 13437 memset (&dbvalue, 0, 6 * sizeof (double)); 13438 position = 0; 13439 13440 if (bytes_per_line > 0) 13441 { 13442 do 13443 { 13444 memset (&buff2, 0, 256 * sizeof (SANE_Byte)); 13445 sumatorio = 0; 13446 /* ptr points to the next position of the first line */ 13447 ptr = buffer + position; 13448 biggest = 0; 13449 lowest = (int) maxvalue; 13450 current_line = 0; 13451 /* Toma los valores de una columna */ 13452 if (mheight > 0) 13453 { 13454 my14b4 = v14b4; 13455 do 13456 { 13457 biggest = max (biggest, *ptr); 13458 13459 if (my14b4 == 0) 13460 { 13461 /*8fd7 */ 13462 if (current_line < mheight) 13463 { 13464 sumatorio += *ptr; 13465 13466 lowest = min (lowest, *ptr); 13467 biggest = max (biggest, *ptr); 13468 13469 buff2[*ptr]++; 13470 } 13471 else 13472 { 13473 /*9011 */ 13474 if (*ptr > lowest) 13475 { 13476 buff2[lowest]--; 13477 buff2[*ptr]++; 13478 sumatorio += *ptr; 13479 sumatorio -= lowest; 13480 13481 if (buff2[lowest] != 0) 13482 { 13483 do 13484 { 13485 lowest++; 13486 } 13487 while (buff2[lowest] == 0); 13488 } 13489 } 13490 } 13491 } 13492 else 13493 sumatorio += *ptr; 13494 /*9067 */ 13495 /* Point to the next pixel under current line */ 13496 ptr += bytes_per_line; 13497 current_line++; 13498 } 13499 while (current_line < mheight); 13500 } 13501 13502 /*908a */ 13503 /* Calculates average of each column */ 13504 sumatorio = sumatorio / mheight; 13505 13506 if (scancfg.colormode != CM_COLOR) 13507 { 13508 channel = 0; 13509 lefdc = position; 13510 } 13511 else 13512 { 13513 /*90c5 */ 13514 if (scancfg.samplerate == PIXEL_RATE) 13515 { 13516 channel = position % lf010; 13517 lefdc = (position / lf010) & 0xffff; 13518 } 13519 else 13520 { 13521 /*90fb */ 13522 channel = position / leff0; 13523 lefdc = position % leff0; 13524 } 13525 } 13526 13527 /*911f */ 13528 dbvalue[channel] += sumatorio; 13529 if ((scancfg.colormode == CM_GRAY) 13530 || (scancfg.colormode == CM_LINEART)) 13531 sumatorio += shadingprediff[scancfg.channel]; 13532 else 13533 sumatorio += shadingprediff[channel]; 13534 13535 /*9151 */ 13536 myst = min (max (0, sumatorio), maxvalue); 13537 13538 /*9198 */ 13539 if (position >= 3) 13540 { 13541 double myst2; 13542 13543 myst -= dbvalue[channel + 3]; 13544 myst2 = myst; 13545 myst = min (myst, shadingprediff[channel + 3]); 13546 13547 my14b4 = -shadingprediff[channel + 3]; 13548 if (myst >= my14b4) 13549 myst = min (myst2, shadingprediff[channel + 3]); 13550 else 13551 myst = my14b4; 13552 13553 myst += dbvalue[channel + 3]; 13554 } 13555 13556 /*9203 */ 13557 dbvalue[channel + 3] = myst; 13558 13559 switch (calibcfg->BShadingOn) 13560 { 13561 case 1: 13562 myCalib->black_shading[channel][lefdc] |= 13563 (unsigned short) (((int) myst & 0xff) << 8) & 0xffff; 13564 break; 13565 case 2: 13566 /*9268 */ 13567 my14b4 = 13568 calibcfg->BRef[channel] / (1 << (8 - scancfg.depth)); 13569 myst -= my14b4; 13570 myst = max (myst, 0); 13571 myst *= mylong; 13572 myCalib->black_shading[channel][lefdc] = min (myst, lefd0); 13573 break; 13574 } 13575 13576 /*92d8 */ 13577 position++; 13578 } 13579 while (position < bytes_per_line); 13580 } 13581 } 13582 13583 /*9306 */ 13584 if (calibcfg->BShadingOn == -2) 13585 { 13586 for (a = 0; a < 3; a++) 13587 { 13588 dbvalue[a] = 13589 (dbvalue[a] / scancfg.coord.width) + calibcfg->ShadingCut[a]; 13590 if (dbvalue[a] < 0) 13591 dbvalue[a] = 0; 13592 smvalues[a] = min ((int) (dbvalue[a] + 0.5) & 0xffff, maxvalue); 13593 } 13594 13595 if (scancfg.coord.width > 0) 13596 { 13597 SANE_Int b, c; 13598 13599 for (c = 0; c < scancfg.coord.width; c++) 13600 for (b = 0; b < 3; b++) 13601 myCalib->black_shading[b][c] |= 13602 (unsigned short) min (smvalues[b] * mylong, lefd0); 13603 } 13604 } 13605 /*9425 */ 13606 free (buffer); 13607 13608 return OK; 13609} 13610 13611static SANE_Int 13612Calibration (struct st_device *dev, SANE_Byte * Regs, 13613 struct st_scanparams *scancfg, struct st_calibration *myCalib, 13614 SANE_Int value) 13615{ 13616 /*//SANE_Int Calibration([fa20]char *Regs, [fa24]struct st_scanparams *scancfg, [fa28]struct st_calibration myCalib, [fa2c]SANE_Int value) 13617 */ 13618 13619 struct st_calibration_config calibcfg; /* f90c */ 13620 SANE_Int a; 13621 SANE_Byte gainmode; 13622 SANE_Int lf900; 13623 13624 DBG (DBG_FNC, "> Calibration\n"); 13625 dbg_ScanParams (scancfg); 13626 13627 (void) value; /*silence gcc */ 13628 13629 memcpy (&calibdata->Regs, Regs, sizeof (SANE_Byte) * RT_BUFFER_LEN); 13630 13631 /*4213be8 */ 13632 memset (&calibcfg, 0x30, sizeof (struct st_calibration_config)); 13633 Calib_LoadConfig (dev, &calibcfg, scan.scantype, scancfg->resolution_x, 13634 scancfg->depth); 13635 13636 memset (&calibdata->gain_offset, 0, sizeof (struct st_gain_offset)); /*[42b3654] */ 13637 for (a = CL_RED; a <= CL_BLUE; a++) 13638 { 13639 myCalib->WRef[a] = calibcfg.WRef[a]; 13640 13641 calibdata->gain_offset.edcg1[a] = 256; 13642 calibdata->gain_offset.odcg1[a] = 256; 13643 calibdata->gain_offset.vgag1[a] = 4; 13644 calibdata->gain_offset.vgag2[a] = 4; 13645 13646 /*3654|3656|3658 13647 365a|365c|365e 13648 3660|3662|3664 13649 3666|3668|366a 13650 366c|366d|366e 13651 366f|3670|3671 13652 3672|3673|3674 */ 13653 } 13654 13655 memcpy (&calibdata->scancfg, scancfg, sizeof (struct st_scanparams)); 13656 gainmode = Lamp_GetGainMode (dev, scancfg->resolution_x, scan.scantype); /* [lf904] = 1 */ 13657 13658 /* 3cf3 */ 13659 myCalib->first_position = 1; 13660 myCalib->shading_type = 0; 13661 if (calibdata->scancfg.colormode == CM_LINEART) 13662 { 13663 calibdata->scancfg.colormode = CM_GRAY; 13664 calibcfg.GainTargetFactor = 1.3; 13665 } 13666 13667 lf900 = OK; 13668 if (calibcfg.CalibPAGOn != 0) 13669 { 13670 if (Calib_PAGain (dev, &calibcfg, gainmode) != 0) 13671 lf900 = ERROR; 13672 /*ERROR*/} 13673 else 13674 { 13675 /*3da7 */ 13676 if ((calibdata->scancfg.colormode != CM_GRAY) 13677 && (calibdata->scancfg.colormode != CM_LINEART)) 13678 { 13679 for (a = CL_RED; a <= CL_BLUE; a++) 13680 calibdata->gain_offset.pag[a] = calibcfg.PAG[a]; 13681 } 13682 else 13683 { 13684 /* 3dd3 */ 13685 /* Default PAGain */ 13686 if (calibdata->scancfg.channel > 2) 13687 calibdata->scancfg.channel = 0; 13688 13689 for (a = CL_RED; a <= CL_BLUE; a++) 13690 calibdata->gain_offset.pag[a] = 13691 calibcfg.PAG[calibdata->scancfg.channel]; 13692 } 13693 } 13694 13695 /* 3e01 */ 13696 if (calibcfg.CalibOffset10n != 0) /*==2*/ 13697 { 13698 /*v14b4=1 offset[CL_RED]=0x174 offset[CL_GREEN]=0x16d offset[CL_BLUE]=0x160 */ 13699 if ((v14b4 != 0) && (offset[CL_RED] != 0) && (offset[CL_GREEN] != 0) 13700 && (offset[CL_BLUE] != 0)) 13701 { 13702 for (a = CL_RED; a <= CL_BLUE; a++) 13703 { 13704 calibdata->gain_offset.edcg1[a] = offset[a]; 13705 calibdata->gain_offset.odcg1[a] = offset[a]; 13706 } 13707 } 13708 else 13709 { 13710 /* 3e84 */ 13711 if ((calibcfg.CalibOffset10n > 0) && (calibcfg.CalibOffset10n < 4)) 13712 { 13713 /*if (calibcfg.CalibOffset10n != 0) */ 13714 if (calibcfg.CalibOffset10n == 3) 13715 { 13716 lf900 = Calib_AdcOffsetRT (dev, &calibcfg, 1); 13717 } 13718 else 13719 { 13720 /* 3eb2 */ 13721 /*falta codigo */ 13722 } 13723 } 13724 } 13725 } 13726 else 13727 { 13728 /* 3faf */ 13729 for (a = CL_RED; a <= CL_BLUE; a++) 13730 { 13731 calibdata->gain_offset.edcg1[a] = 13732 abs (calibcfg.OffsetEven1[a] - 0x100); 13733 calibdata->gain_offset.odcg1[a] = 13734 abs (calibcfg.OffsetOdd1[a] - 0x100); 13735 } 13736 } 13737 13738 /* 3f13 3f0b */ 13739 if ((gainmode != 0) && (calibcfg.CalibGain10n != 0)) 13740 { 13741 /*gain[CL_RED]=0x17 gain[CL_GREEN]=0x12 gain[CL_BLUE]=0x17 */ 13742 if ((v14b4 != 0) && (gain[CL_RED] != 0) && (gain[CL_GREEN] != 0) 13743 && (gain[CL_BLUE] != 0)) 13744 { 13745 for (a = CL_RED; a <= CL_BLUE; a++) 13746 calibdata->gain_offset.vgag1[a] = gain[a]; 13747 } 13748 else 13749 { 13750 /*4025 */ 13751 lf900 = Calib_AdcGain (dev, &calibcfg, 1, gainmode); 13752 13753 if ((v14b4 != 0) && (lf900 == OK)) 13754 GainOffset_Save (dev, &calibdata->gain_offset.edcg1[0], 13755 &calibdata->gain_offset.vgag1[0]); 13756 } 13757 } 13758 else 13759 { 13760 /*4089 */ 13761 for (a = CL_RED; a <= CL_BLUE; a++) 13762 calibdata->gain_offset.vgag1[a] = calibcfg.Gain1[a]; 13763 } 13764 13765 /*40a5 */ 13766 if ((gainmode != 0) && (calibcfg.CalibOffset20n != 0)) 13767 { 13768 switch (calibcfg.CalibOffset20n) 13769 { 13770 case 3: 13771 lf900 = Calib_AdcOffsetRT (dev, &calibcfg, 2); 13772 break; 13773 } 13774 /*4140 */ 13775 /*falta codigo */ 13776 } 13777 else 13778 { 13779 /*4162 */ 13780 for (a = CL_RED; a <= CL_BLUE; a++) 13781 { 13782 calibdata->gain_offset.edcg2[a] = 13783 abs (calibcfg.OffsetEven2[a] - 0x40); 13784 calibdata->gain_offset.odcg2[a] = 13785 abs (calibcfg.OffsetOdd2[a] - 0x40); 13786 } 13787 } 13788 13789 /*41d6 */ 13790 if ((gainmode != 0) && (calibcfg.CalibGain20n != 0)) 13791 { 13792 lf900 = Calib_AdcGain (dev, &calibcfg, 0, gainmode); 13793 } 13794 else 13795 { 13796 /*423c */ 13797 for (a = CL_RED; a <= CL_BLUE; a++) 13798 calibdata->gain_offset.vgag2[a] = calibcfg.Gain2[a]; 13799 } 13800 13801 /*4258 */ 13802 if (calibcfg.TotShading != 0) 13803 { 13804 lf900 = Calib_BWShading (&calibcfg, myCalib, gainmode); 13805 /*falta codigo */ 13806 } 13807 else 13808 { 13809 /*428f */ 13810 if (gainmode != 0) 13811 { 13812 if (calibcfg.BShadingOn != 0) 13813 lf900 = Calib_BlackShading (dev, &calibcfg, myCalib, gainmode); 13814 13815 /*42fd */ 13816 if ((lf900 != ERROR) && (calibcfg.WShadingOn != 0)) 13817 { 13818 switch (calibcfg.WShadingOn) 13819 { 13820 default: 13821 break; 13822 case 3: 13823 lf900 = 13824 Calib_WhiteShading_3 (dev, &calibcfg, myCalib, gainmode); 13825 break; 13826 case 2: 13827 break; 13828 } 13829 } 13830 else 13831 myCalib->shading_enabled = FALSE; 13832 } 13833 else 13834 myCalib->shading_enabled = FALSE; 13835 } 13836 13837 /*43ca */ 13838 memcpy (&myCalib->gain_offset, &calibdata->gain_offset, 13839 sizeof (struct st_gain_offset)); 13840 memcpy (&mitabla2, &calibdata->gain_offset, sizeof (struct st_gain_offset)); 13841 13842 /*4424 */ 13843 /* Park home after calibration */ 13844 if (get_value (SCANINFO, PARKHOMEAFTERCALIB, TRUE, FITCALIBRATE) == FALSE) 13845 scan.ler -= calibcfg.WShadingHeight; 13846 else 13847 Head_ParkHome (dev, TRUE, dev->motorcfg->parkhomemotormove); 13848 13849 return OK; 13850} 13851 13852/*static void show_diff(struct st_device *dev, SANE_Byte *original) 13853{ 13854 SANE_Byte *buffer = (SANE_Byte *)malloc(RT_BUFFER_LEN * sizeof(SANE_Byte)); 13855 SANE_Int a; 13856 13857 if ((buffer == NULL)||(original == NULL)) 13858 return; 13859 13860 if (RTS_ReadRegs(dev->usb_handle, buffer) != OK) 13861 { 13862 free(buffer); 13863 return; 13864 } 13865 13866 for (a = 0; a < RT_BUFFER_LEN; a++) 13867 { 13868 if ((original[a] & 0xff) != (buffer[a] & 0xff)) 13869 { 13870 printf("%5i: %i -> %i\n", a, original[a] & 0xff, buffer[a] & 0xff); 13871 original[a] = buffer[a] & 0xff; 13872 } 13873 } 13874 13875 free(buffer); 13876} */ 13877 13878static SANE_Int 13879Load_Constrains (struct st_device *dev) 13880{ 13881 SANE_Int rst = ERROR; 13882 13883 if (dev->constrains != NULL) 13884 Free_Constrains (dev); 13885 13886 DBG (DBG_FNC, "> Load_Constrains\n"); 13887 13888 dev->constrains = 13889 (struct st_constrains *) malloc (sizeof (struct st_constrains)); 13890 if (dev->constrains != NULL) 13891 { 13892 cfg_constrains_get (dev->constrains); 13893 rst = OK; 13894 } 13895 13896 return rst; 13897} 13898 13899static SANE_Int 13900Constrains_Check (struct st_device *dev, SANE_Int Resolution, 13901 SANE_Int scantype, struct st_coords *mycoords) 13902{ 13903 /* 13904 Constrains: 13905 100 dpi 850 x 1170 | 164 x 327 13906 300 dpi 2550 x 3510 13907 600 dpi 5100 x 7020 13908 1200 dpi 10200 x 14040 13909 */ 13910 13911 SANE_Int rst = ERROR; 13912 13913 if (dev->constrains != NULL) 13914 { 13915 struct st_coords coords; 13916 struct st_coords *mc; 13917 13918 if ((scantype < ST_NORMAL) || (scantype > ST_NEG)) 13919 scantype = ST_NORMAL; 13920 13921 switch (scantype) 13922 { 13923 case ST_TA: 13924 mc = &dev->constrains->slide; 13925 break; 13926 case ST_NEG: 13927 mc = &dev->constrains->negative; 13928 break; 13929 default: 13930 mc = &dev->constrains->reflective; 13931 break; 13932 } 13933 13934 coords.left = MM_TO_PIXEL (mc->left, Resolution); 13935 coords.width = MM_TO_PIXEL (mc->width, Resolution); 13936 coords.top = MM_TO_PIXEL (mc->top, Resolution); 13937 coords.height = MM_TO_PIXEL (mc->height, Resolution); 13938 13939 /* Check left and top */ 13940 if (mycoords->left < 0) 13941 mycoords->left = 0; 13942 13943 mycoords->left += coords.left; 13944 13945 if (mycoords->top < 0) 13946 mycoords->top = 0; 13947 13948 mycoords->top += coords.top; 13949 13950 /* Check width and height */ 13951 if ((mycoords->width < 0) || (mycoords->width > coords.width)) 13952 mycoords->width = coords.width; 13953 13954 if ((mycoords->height < 0) || (mycoords->height > coords.height)) 13955 mycoords->height = coords.height; 13956 13957 rst = OK; 13958 } 13959 13960 DBG (DBG_FNC, 13961 "> Constrains_Check: Source=%s, Res=%i, LW=(%i,%i), TH=(%i,%i): %i\n", 13962 dbg_scantype (scantype), Resolution, mycoords->left, mycoords->width, 13963 mycoords->top, mycoords->height, rst); 13964 13965 return rst; 13966} 13967 13968static struct st_coords * 13969Constrains_Get (struct st_device *dev, SANE_Byte scantype) 13970{ 13971 static struct st_coords *rst = NULL; 13972 13973 if (dev->constrains != NULL) 13974 { 13975 switch (scantype) 13976 { 13977 case ST_TA: 13978 rst = &dev->constrains->slide; 13979 break; 13980 case ST_NEG: 13981 rst = &dev->constrains->negative; 13982 break; 13983 default: 13984 rst = &dev->constrains->reflective; 13985 break; 13986 } 13987 } 13988 13989 return rst; 13990} 13991 13992static void 13993Free_Constrains (struct st_device *dev) 13994{ 13995 DBG (DBG_FNC, "> Free_Constrains\n"); 13996 13997 if (dev->constrains != NULL) 13998 { 13999 free (dev->constrains); 14000 dev->constrains = NULL; 14001 } 14002} 14003 14004static void 14005RTS_DebugInit () 14006{ 14007 /* Default values */ 14008 RTS_Debug->dev_model = HP3970; 14009 14010 RTS_Debug->DumpShadingData = FALSE; 14011 RTS_Debug->SaveCalibFile = FALSE; 14012 RTS_Debug->ScanWhiteBoard = FALSE; 14013 RTS_Debug->EnableGamma = TRUE; 14014 RTS_Debug->use_fixed_pwm = TRUE; 14015 RTS_Debug->dmatransfersize = 0x80000; 14016 RTS_Debug->dmasetlength = 0x7c0000; 14017 RTS_Debug->dmabuffersize = 0x400000; 14018 RTS_Debug->usbtype = -1; 14019 14020 /* Lamp settings */ 14021 RTS_Debug->overdrive_flb = 10000; /* msecs */ 14022 RTS_Debug->overdrive_ta = 10000; /* msecs */ 14023 14024 RTS_Debug->warmup = TRUE; 14025 14026 /* Calibration settings */ 14027 RTS_Debug->calibrate = FALSE; 14028 RTS_Debug->wshading = TRUE; 14029} 14030 14031static void 14032RTS_Setup_Gamma (SANE_Byte * Regs, struct st_hwdconfig *hwdcfg) 14033{ 14034 DBG (DBG_FNC, "> RTS_Setup_Gamma(*Regs, *hwdcfg)\n"); 14035 14036 if ((hwdcfg != NULL) && (Regs != NULL)) 14037 { 14038 if (hwdcfg->use_gamma_tables != FALSE) 14039 { 14040 SANE_Int table_size; 14041 14042 /* set set table size */ 14043 data_bitset (&Regs[0x1d0], 0x0f, hwdcfg->gamma_tablesize); 14044 14045 /* enable gamma correction */ 14046 data_bitset (&Regs[0x1d0], 0x40, 1); 14047 14048 14049 switch (Regs[0x1d0] & 0x0c) 14050 { 14051 case 0: 14052 table_size = (Regs[0x1d0] & 1) | 0x0100; 14053 break; 14054 case 4: 14055 table_size = (Regs[0x1d0] & 1) | 0x0400; 14056 break; 14057 case 8: 14058 table_size = (Regs[0x1d0] & 1) | 0x1000; 14059 break; 14060 default: 14061 table_size = hwdcfg->startpos & 0xffff; 14062 break; 14063 } 14064 14065 /* 5073 */ 14066 /* points to red gamma table */ 14067 data_wide_bitset (&Regs[0x1b4], 0x3fff, 0); 14068 14069 /* points to green gamma table */ 14070 data_wide_bitset (&Regs[0x1b6], 0x3fff, table_size); 14071 14072 /* points to blue gamma table */ 14073 data_wide_bitset (&Regs[0x1b8], 0x3fff, table_size * 2); 14074 14075 v15f8 = (((table_size * 3) + 15) / 16) & 0xffff; 14076 } 14077 else 14078 { 14079 /* disable gamma correction */ 14080 data_bitset (&Regs[0x1d0], 0x40, 0); 14081 v15f8 = 0; 14082 } 14083 } 14084} 14085 14086static SANE_Int 14087RTS_USBType (struct st_device *dev) 14088{ 14089 /* Gets USB type of this scanner */ 14090 14091 SANE_Int rst = ERROR; 14092 SANE_Byte data; 14093 14094 DBG (DBG_FNC, "+ RTS_USBType\n"); 14095 14096 if (Read_Byte (dev->usb_handle, 0xfe11, &data) == OK) 14097 rst = (data & 1); 14098 14099 DBG (DBG_FNC, "- RTS_USBType(void): %s\n", 14100 (rst == USB11) ? "USB1.1" : "USB2.0"); 14101 14102 return rst; 14103} 14104 14105static SANE_Int 14106Init_Vars (void) 14107{ 14108 SANE_Int rst = OK; 14109 14110 hp_gamma = malloc (sizeof (struct st_gammatables)); 14111 if (hp_gamma != NULL) 14112 memset (hp_gamma, 0, sizeof (struct st_gammatables)); 14113 else 14114 rst = ERROR; 14115 14116 if (rst == OK) 14117 { 14118 RTS_Debug = malloc (sizeof (struct st_debug_opts)); 14119 if (RTS_Debug != NULL) 14120 memset (RTS_Debug, 0, sizeof (struct st_debug_opts)); 14121 else 14122 rst = ERROR; 14123 } 14124 14125 if (rst == OK) 14126 { 14127 default_gain_offset = malloc (sizeof (struct st_gain_offset)); 14128 if (default_gain_offset != NULL) 14129 memset (default_gain_offset, 0, sizeof (struct st_gain_offset)); 14130 else 14131 rst = ERROR; 14132 } 14133 14134 if (rst == OK) 14135 { 14136 calibdata = malloc (sizeof (struct st_calibration_data)); 14137 if (calibdata != NULL) 14138 memset (calibdata, 0, sizeof (struct st_calibration_data)); 14139 else 14140 rst = ERROR; 14141 } 14142 14143 if (rst == OK) 14144 { 14145 wshading = malloc (sizeof (struct st_shading)); 14146 if (wshading != NULL) 14147 memset (wshading, 0, sizeof (struct st_shading)); 14148 else 14149 rst = ERROR; 14150 } 14151 14152 waitforpwm = TRUE; 14153 14154 use_gamma_tables = TRUE; 14155 14156 if (rst == OK) 14157 RTS_DebugInit (); 14158 else 14159 Free_Vars (); 14160 14161 return rst; 14162} 14163 14164static void 14165Free_Vars (void) 14166{ 14167 if (RTS_Debug != NULL) 14168 { 14169 free (RTS_Debug); 14170 RTS_Debug = NULL; 14171 } 14172 14173 if (hp_gamma != NULL) 14174 { 14175 free (hp_gamma); 14176 hp_gamma = NULL; 14177 } 14178 14179 if (calibdata != NULL) 14180 { 14181 free (calibdata); 14182 calibdata = NULL; 14183 } 14184 14185 if (wshading != NULL) 14186 { 14187 if (wshading->rates != NULL) 14188 free (wshading->rates); 14189 14190 free (wshading); 14191 wshading = NULL; 14192 } 14193 14194 if (default_gain_offset != NULL) 14195 { 14196 free (default_gain_offset); 14197 default_gain_offset = NULL; 14198 } 14199 14200} 14201 14202static SANE_Int 14203Chipset_Reset (struct st_device *dev) 14204{ 14205 SANE_Int rst; 14206 14207 DBG (DBG_FNC, "+ Chipset_Reset:\n"); 14208 14209 /* I've found two ways to reset chipset. Next one will stay commented 14210 rst = ERROR; 14211 if (Read_Byte(dev->usb_handle, 0xe800, &data) == OK) 14212 { 14213 data |= 0x20; 14214 if (Write_Byte(dev->usb_handle, 0xe800, data) == OK) 14215 { 14216 data &= 0xdf; 14217 rst = Write_Byte(dev->usb_handle, 0xe800, data); 14218 } 14219 } 14220 */ 14221 14222 rst = IWrite_Buffer (dev->usb_handle, 0x0000, NULL, 0, 0x0801); 14223 14224 DBG (DBG_FNC, "- Chipset_Reset: %i\n", rst); 14225 14226 return rst; 14227} 14228 14229static SANE_Int 14230RTS_DMA_Enable_Read (struct st_device *dev, SANE_Int dmacs, SANE_Int size, 14231 SANE_Int options) 14232{ 14233 SANE_Int rst = ERROR; 14234 SANE_Byte buffer[6]; 14235 14236 DBG (DBG_FNC, 14237 "+ RTS_DMA_Enable_Read(dmacs=0x%04x, size=%i, options=0x%06x)\n", 14238 dmacs, size, options); 14239 14240 data_msb_set (&buffer[0], options, 3); 14241 14242 /* buffer size divided by 2 (words count) */ 14243 data_lsb_set (&buffer[3], size / 2, 3); 14244 14245 rst = IWrite_Buffer (dev->usb_handle, dmacs, buffer, 6, 0x0400); 14246 14247 DBG (DBG_FNC, "- RTS_DMA_Enable_Read: %i\n", rst); 14248 14249 return rst; 14250} 14251 14252static SANE_Int 14253RTS_DMA_Enable_Write (struct st_device *dev, SANE_Int dmacs, SANE_Int size, 14254 SANE_Int options) 14255{ 14256 SANE_Int rst = ERROR; 14257 SANE_Byte buffer[6]; 14258 14259 DBG (DBG_FNC, 14260 "+ RTS_DMA_Enable_Write(dmacs=0x%04x, size=%i, options=0x%06x)\n", 14261 dmacs, size, options); 14262 14263 data_msb_set (&buffer[0], options, 3); 14264 14265 /* buffer size divided by 2 (words count) */ 14266 data_lsb_set (&buffer[3], size / 2, 3); 14267 14268 rst = IWrite_Buffer (dev->usb_handle, dmacs, buffer, 6, 0x0401); 14269 14270 DBG (DBG_FNC, "- RTS_DMA_Enable_Write: %i\n", rst); 14271 14272 return rst; 14273} 14274 14275static SANE_Int 14276RTS_DMA_Cancel (struct st_device *dev) 14277{ 14278 SANE_Int rst; 14279 14280 DBG (DBG_FNC, "+ RTS_DMA_Cancel:\n"); 14281 14282 rst = IWrite_Word (dev->usb_handle, 0x0000, 0, 0x0600); 14283 14284 DBG (DBG_FNC, "- RTS_DMA_Cancel: %i\n", rst); 14285 14286 return rst; 14287} 14288 14289static SANE_Int 14290RTS_DMA_Reset (struct st_device *dev) 14291{ 14292 SANE_Int rst; 14293 14294 DBG (DBG_FNC, "+ RTS_DMA_Reset:\n"); 14295 14296 rst = IWrite_Word (dev->usb_handle, 0x0000, 0x0000, 0x0800); 14297 14298 DBG (DBG_FNC, "- RTS_DMA_Reset: %i\n", rst); 14299 14300 return rst; 14301} 14302 14303static SANE_Int 14304RTS_EEPROM_WriteByte (USB_Handle usb_handle, SANE_Int address, SANE_Byte data) 14305{ 14306 SANE_Int rst; 14307 14308 DBG (DBG_FNC, "+ RTS_EEPROM_WriteByte(address=%04x, data=%i):\n", address, 14309 data); 14310 14311 rst = IWrite_Byte (usb_handle, address, data, 0x200, 0x200); 14312 14313 DBG (DBG_FNC, "- RTS_EEPROM_WriteByte: %i\n", rst); 14314 14315 return rst; 14316} 14317 14318static SANE_Int 14319RTS_EEPROM_ReadWord (USB_Handle usb_handle, SANE_Int address, SANE_Int * data) 14320{ 14321 SANE_Int rst; 14322 14323 DBG (DBG_FNC, "+ RTS_EEPROM_ReadWord(address=%04x, data):\n", address); 14324 14325 rst = IRead_Word (usb_handle, address, data, 0x200); 14326 14327 DBG (DBG_FNC, "- RTS_EEPROM_ReadWord: %i\n", rst); 14328 14329 return rst; 14330} 14331 14332static SANE_Int 14333RTS_EEPROM_ReadByte (USB_Handle usb_handle, SANE_Int address, 14334 SANE_Byte * data) 14335{ 14336 SANE_Int rst; 14337 14338 DBG (DBG_FNC, "+ RTS_EEPROM_ReadByte(address=%04x, data):\n", address); 14339 14340 rst = IRead_Byte (usb_handle, address, data, 0x200); 14341 14342 DBG (DBG_FNC, "- RTS_EEPROM_ReadByte: %i\n", rst); 14343 14344 return rst; 14345} 14346 14347static SANE_Int 14348RTS_EEPROM_WriteWord (USB_Handle usb_handle, SANE_Int address, SANE_Int data) 14349{ 14350 SANE_Int rst; 14351 14352 DBG (DBG_FNC, "+ RTS_EEPROM_WriteWord(address=%04x, data=%i):\n", address, 14353 data); 14354 14355 rst = IWrite_Word (usb_handle, address, data, 0x0200); 14356 14357 DBG (DBG_FNC, "- RTS_EEPROM_WriteWord: %i\n", rst); 14358 14359 return rst; 14360} 14361 14362static SANE_Int 14363RTS_EEPROM_ReadInteger (USB_Handle usb_handle, SANE_Int address, 14364 SANE_Int * data) 14365{ 14366 SANE_Int rst; 14367 14368 DBG (DBG_FNC, "+ RTS_EEPROM_ReadInteger(address=%04x, data):\n", address); 14369 14370 rst = IRead_Integer (usb_handle, address, data, 0x200); 14371 14372 DBG (DBG_FNC, "- RTS_EEPROM_ReadInteger: %i\n", rst); 14373 14374 return rst; 14375} 14376 14377static SANE_Int 14378RTS_EEPROM_WriteInteger (USB_Handle usb_handle, SANE_Int address, 14379 SANE_Int data) 14380{ 14381 SANE_Int rst; 14382 14383 DBG (DBG_FNC, "+ RTS_EEPROM_WriteInteger(address=%04x, data):\n", address); 14384 14385 rst = IWrite_Integer (usb_handle, address, data, 0x200); 14386 14387 DBG (DBG_FNC, "- RTS_EEPROM_WriteInteger: %i\n", rst); 14388 14389 return rst; 14390} 14391 14392static SANE_Int 14393RTS_EEPROM_WriteBuffer (USB_Handle usb_handle, SANE_Int address, 14394 SANE_Byte * data, SANE_Int size) 14395{ 14396 SANE_Int rst; 14397 14398 DBG (DBG_FNC, "+ RTS_EEPROM_WriteBuffer(address=%04x, data, size=%i):\n", 14399 address, size); 14400 14401 rst = IWrite_Buffer (usb_handle, address, data, size, 0x200); 14402 14403 DBG (DBG_FNC, "- RTS_EEPROM_WriteBuffer: %i\n", rst); 14404 14405 return rst; 14406} 14407 14408static void 14409WShading_Emulate (SANE_Byte * buffer, SANE_Int * chnptr, SANE_Int size, 14410 SANE_Int depth) 14411{ 14412 if ((wshading->rates != NULL) && (chnptr != NULL)) 14413 { 14414 if (*chnptr < wshading->count) 14415 { 14416 double maxvalue, chncolor; 14417 SANE_Int chnsize; 14418 SANE_Int pos; 14419 SANE_Int icolor; 14420 14421 maxvalue = (1 << depth) - 1; 14422 chnsize = (depth > 8) ? 2 : 1; 14423 14424 pos = 0; 14425 while (pos < size) 14426 { 14427 /* get channel color */ 14428 chncolor = data_lsb_get (buffer + pos, chnsize); 14429 14430 /* apply shading coefficient */ 14431 chncolor *= wshading->rates[*chnptr]; 14432 14433 /* care about limits */ 14434 chncolor = min (chncolor, maxvalue); 14435 14436 /* save color */ 14437 icolor = chncolor; 14438 data_lsb_set (buffer + pos, icolor, chnsize); 14439 14440 *chnptr = *chnptr + 1; 14441 if (*chnptr >= wshading->count) 14442 *chnptr = 0; 14443 14444 pos += chnsize; 14445 } 14446 } 14447 } 14448} 14449 14450static SANE_Int 14451WShading_Calibrate (struct st_device *dev, SANE_Byte * Regs, 14452 struct st_calibration *myCalib, 14453 struct st_scanparams *scancfg) 14454{ 14455 struct st_calibration_config *calibcfg; 14456 struct st_gain_offset myCalibTable; 14457 struct st_scanparams *myscancfg; 14458 SANE_Byte *myRegs; /*f1bc */ 14459 SANE_Int bytes_per_line; 14460 /**/ SANE_Int x, y, a, C; 14461 SANE_Byte *pattern; /*f164 */ 14462 double sumatorio; 14463 SANE_Int gainmode; 14464 SANE_Int rst; 14465 SANE_Byte *avg_colors; 14466 14467 DBG (DBG_FNC, "> WShading_Calibrate(*myCalib)\n"); 14468 14469 memset (&myCalibTable, 0, sizeof (struct st_gain_offset)); 14470 for (C = CL_RED; C <= CL_BLUE; C++) 14471 { 14472 myCalibTable.pag[C] = 3; 14473 myCalibTable.vgag1[C] = 4; 14474 myCalibTable.vgag2[C] = 4; 14475 } 14476 14477 calibcfg = 14478 (struct st_calibration_config *) 14479 malloc (sizeof (struct st_calibration_config)); 14480 memset (calibcfg, 0x30, sizeof (struct st_calibration_config)); 14481 14482 myscancfg = (struct st_scanparams *) malloc (sizeof (struct st_scanparams)); 14483 memcpy (myscancfg, scancfg, sizeof (struct st_scanparams)); 14484 14485 myRegs = (SANE_Byte *) malloc (RT_BUFFER_LEN * sizeof (SANE_Byte)); 14486 memcpy (myRegs, Regs, RT_BUFFER_LEN * sizeof (SANE_Byte)); 14487 14488 Calib_LoadConfig (dev, calibcfg, scan.scantype, myscancfg->resolution_x, 14489 myscancfg->depth); 14490 gainmode = Lamp_GetGainMode (dev, myscancfg->resolution_x, scan.scantype); 14491 14492 Lamp_SetGainMode (dev, myRegs, myscancfg->resolution_x, gainmode); 14493 14494 rst = OK; 14495 14496 switch (scan.scantype) 14497 { 14498 case ST_NORMAL: 14499 /*a184 */ 14500 myscancfg->coord.left += scan.ser; 14501 myscancfg->coord.width &= 0xffff; 14502 break; 14503 case ST_TA: 14504 case ST_NEG: 14505 myscancfg->coord.left += scan.ser; 14506 break; 14507 } 14508 14509 /*a11b */ 14510 if ((myscancfg->coord.width & 1) != 0) 14511 myscancfg->coord.width++; 14512 14513 myscancfg->coord.top = 1; 14514 myscancfg->coord.height = calibcfg->WShadingHeight; 14515 14516 myscancfg->sensorresolution = 0; 14517 14518 bytes_per_line = 14519 myscancfg->coord.width * (((myscancfg->colormode == CM_COLOR) ? 3 : 1) * 14520 ((myscancfg->depth > 8) ? 2 : 1)); 14521 14522 /*a1e8 */ 14523 myscancfg->v157c = bytes_per_line; 14524 myscancfg->bytesperline = bytes_per_line; 14525 14526 /* allocate space for pattern */ 14527 pattern = 14528 (SANE_Byte *) malloc (((myscancfg->coord.height) * bytes_per_line) * 14529 sizeof (SANE_Byte)); 14530 if (pattern == NULL) 14531 return ERROR; 14532 14533 /* Scan image */ 14534 myCalib->shading_enabled = FALSE; 14535 rst = 14536 RTS_GetImage (dev, myRegs, myscancfg, &myCalibTable, pattern, myCalib, 14537 0x20000000, gainmode); 14538 14539 if (rst != ERROR) 14540 { 14541 SANE_Int chn; 14542 double colors[3] = { 0, 0, 0 }; 14543 double prueba; 14544 SANE_Int data; 14545 SANE_Int bytes_per_channel; 14546 14547 bytes_per_channel = (myscancfg->depth > 8) ? 2 : 1; 14548 14549 avg_colors = (SANE_Byte *) malloc (sizeof (SANE_Byte) * bytes_per_line); 14550 14551 if (avg_colors != NULL) 14552 { 14553 wshading->ptr = 0; 14554 wshading->count = bytes_per_line / bytes_per_channel; 14555 14556 if (wshading->rates != NULL) 14557 { 14558 free (wshading->rates); 14559 wshading->rates = NULL; 14560 } 14561 wshading->rates = 14562 (double *) malloc (sizeof (double) * wshading->count); 14563 14564 chn = 0; 14565 for (x = 0; x < wshading->count; x++) 14566 { 14567 sumatorio = 0; 14568 14569 for (y = 0; y < myscancfg->coord.height; y++) 14570 { 14571 data = 14572 data_lsb_get (pattern + 14573 ((x * bytes_per_channel) + 14574 (bytes_per_line * y)), bytes_per_channel); 14575 sumatorio += data; 14576 } 14577 14578 sumatorio /= myscancfg->coord.height; 14579 a = sumatorio; 14580 colors[chn] = max (colors[chn], sumatorio); 14581 chn++; 14582 if (chn > 2) 14583 chn = 0; 14584 14585 data_lsb_set (avg_colors + (x * bytes_per_channel), a, 14586 bytes_per_channel); 14587 } 14588 14589 DBG (DBG_FNC, " -> max colors RGB= %f %f %f\n", colors[0], 14590 colors[1], colors[2]); 14591 14592 chn = 0; 14593 for (x = 0; x < wshading->count; x++) 14594 { 14595 data = 14596 data_lsb_get (avg_colors + (x * bytes_per_channel), 14597 bytes_per_channel); 14598 prueba = data; 14599 *(wshading->rates + x) = colors[chn] / prueba; 14600 chn++; 14601 if (chn > 2) 14602 chn = 0; 14603 } 14604 } 14605 14606 if (RTS_Debug->SaveCalibFile != FALSE) 14607 { 14608 dbg_tiff_save ("whiteshading_jkd.tiff", 14609 myscancfg->coord.width, 14610 myscancfg->coord.height, 14611 myscancfg->depth, 14612 CM_COLOR, 14613 scancfg->resolution_x, 14614 scancfg->resolution_y, 14615 pattern, (myscancfg->coord.height) * bytes_per_line); 14616 } 14617 14618#ifdef developing 14619 { 14620 FILE *archivo; 14621 char texto[1024]; 14622 14623 /* apply correction to the pattern to see the result */ 14624 chn = 0; 14625 for (x = 0; x < myscancfg->coord.height * wshading->count; x++) 14626 { 14627 data = 14628 data_lsb_get (pattern + (x * bytes_per_channel), 14629 bytes_per_channel); 14630 sumatorio = data; 14631 sumatorio *= wshading->rates[chn]; 14632 if (sumatorio > ((1 << myscancfg->depth) - 1)) 14633 sumatorio = (1 << myscancfg->depth) - 1; 14634 14635 a = sumatorio; 14636 data_lsb_set (pattern + (x * bytes_per_channel), a, 14637 bytes_per_channel); 14638 14639 chn++; 14640 if (chn == wshading->count) 14641 chn = 0; 14642 } 14643 14644 /* save corrected pattern */ 14645 dbg_tiff_save ("onwhiteshading_jkd.tiff", 14646 myscancfg->coord.width, 14647 myscancfg->coord.height, 14648 myscancfg->depth, 14649 CM_COLOR, 14650 scancfg->resolution_x, 14651 scancfg->resolution_y, 14652 pattern, (myscancfg->coord.height) * bytes_per_line); 14653 14654 /* export coefficients */ 14655 archivo = fopen ("wShading.txt", "w"); 14656 for (x = 0; x < wshading->count; x++) 14657 { 14658 snprintf (texto, 1024, "%f", wshading->rates[x]); 14659 fprintf (archivo, "%s\n", texto); 14660 } 14661 14662 fclose (archivo); 14663 } 14664#endif 14665 } 14666 14667 free (pattern); 14668 14669 return OK; 14670} 14671 14672#ifdef developing 14673static SANE_Int 14674motor_pos (struct st_device *dev, SANE_Byte * Regs, 14675 struct st_calibration *myCalib, struct st_scanparams *scancfg) 14676{ 14677 struct st_calibration_config *calibcfg; 14678 struct st_gain_offset myCalibTable; 14679 struct st_scanparams *myscancfg; 14680 SANE_Byte *myRegs; /*f1bc */ 14681 SANE_Int bytes_per_line; 14682 /**/ SANE_Int a, C; 14683 SANE_Byte *scanbuffer; /*f164 */ 14684 SANE_Int gainmode; 14685 SANE_Int rst; 14686 14687 DBG (DBG_FNC, "> Calib_test(*myCalib)\n"); 14688 14689 memset (&myCalibTable, 0, sizeof (struct st_gain_offset)); 14690 14691 calibcfg = 14692 (struct st_calibration_config *) 14693 malloc (sizeof (struct st_calibration_config)); 14694 memset (calibcfg, 0x30, sizeof (struct st_calibration_config)); 14695 14696 myscancfg = (struct st_scanparams *) malloc (sizeof (struct st_scanparams)); 14697 memcpy (myscancfg, scancfg, sizeof (struct st_scanparams)); 14698 14699 myRegs = (SANE_Byte *) malloc (RT_BUFFER_LEN * sizeof (SANE_Byte)); 14700 memcpy (myRegs, Regs, RT_BUFFER_LEN * sizeof (SANE_Byte)); 14701 14702 Calib_LoadConfig (dev, calibcfg, scan.scantype, myscancfg->resolution_x, 14703 myscancfg->depth); 14704 gainmode = Lamp_GetGainMode (dev, myscancfg->resolution_x, scan.scantype); 14705 14706 Lamp_SetGainMode (dev, myRegs, myscancfg->resolution_x, gainmode); 14707 14708 rst = OK; 14709 14710 switch (scan.scantype) 14711 { 14712 case ST_NORMAL: 14713 /*a184 */ 14714 myscancfg->coord.left += scan.ser; 14715 myscancfg->coord.width &= 0xffff; 14716 break; 14717 case ST_TA: 14718 case ST_NEG: 14719 myscancfg->coord.left += scan.ser; 14720 break; 14721 } 14722 14723 /*a11b */ 14724 if ((myscancfg->coord.width & 1) != 0) 14725 myscancfg->coord.width++; 14726 14727 myscancfg->coord.top = 100; 14728 myscancfg->coord.height = 30; 14729 14730 bytes_per_line = myscancfg->coord.width * 3; 14731 14732 /*a1e8 */ 14733 myscancfg->v157c = bytes_per_line; 14734 myscancfg->bytesperline = bytes_per_line; 14735 14736 scanbuffer = 14737 (SANE_Byte *) malloc (((myscancfg->coord.height + 16) * bytes_per_line) * 14738 sizeof (SANE_Byte)); 14739 if (scanbuffer == NULL) 14740 return ERROR; 14741 14742 /* Scan image */ 14743 myCalib->shading_enabled = FALSE; 14744 /*Head_Relocate(dev, dev->motorcfg->highspeedmotormove, MTR_FORWARD, 5500); */ 14745 14746 for (a = 0; a < 10; a++) 14747 { 14748 for (C = CL_RED; C <= CL_BLUE; C++) 14749 { 14750 myCalibTable.pag[C] = 3; 14751 myCalibTable.vgag1[C] = 4; 14752 myCalibTable.vgag2[C] = 4; 14753 myCalibTable.edcg1[C] = a * 20; 14754 } 14755 14756 dbg_ScanParams (myscancfg); 14757 14758 Head_Relocate (dev, dev->motorcfg->highspeedmotormove, MTR_FORWARD, 14759 5000); 14760 rst = 14761 RTS_GetImage (dev, myRegs, myscancfg, &myCalibTable, scanbuffer, 14762 myCalib, 0x20000000, gainmode); 14763 Head_ParkHome (dev, TRUE, dev->motorcfg->parkhomemotormove); 14764 14765 if (rst != ERROR) 14766 { 14767 char name[30]; 14768 snprintf (name, 30, "calibtest-%i.tiff", a); 14769 dbg_tiff_save (name, 14770 myscancfg->coord.width, 14771 myscancfg->coord.height, 14772 myscancfg->depth, 14773 CM_COLOR, 14774 myscancfg->resolution_x, 14775 myscancfg->resolution_y, 14776 scanbuffer, 14777 (myscancfg->coord.height + 16) * bytes_per_line); 14778 } 14779 } 14780 14781 free (scanbuffer); 14782 14783 exit (0); 14784 return OK; 14785} 14786 14787static SANE_Int 14788hp4370_prueba (struct st_device *dev) 14789{ 14790 SANE_Int rst; 14791 SANE_Int data = 0x0530, a; 14792 SANE_Int transferred; 14793 SANE_Byte buffer[512]; 14794 14795 for (a = 0; a < 256; a++) 14796 data_lsb_set (buffer + (a * 2), 0x9d7, 2); 14797 14798 rst = IWrite_Word (dev->usb_handle, 0x0000, data, 0x0800); 14799 RTS_DMA_Enable_Write (dev, 0x4, 512, 0); 14800 Bulk_Operation (dev, BLK_WRITE, 512, buffer, &transferred); 14801 14802 return rst; 14803} 14804 14805static SANE_Int 14806Calib_BlackShading_jkd (struct st_device *dev, SANE_Byte * Regs, 14807 struct st_calibration *myCalib, 14808 struct st_scanparams *scancfg) 14809{ 14810 struct st_calibration_config *calibcfg; 14811 struct st_gain_offset myCalibTable; 14812 struct st_scanparams *myscancfg; 14813 SANE_Byte *myRegs; /*f1bc */ 14814 SANE_Int bytes_per_line; 14815 /**/ SANE_Int x, y, a, C; 14816 SANE_Byte *scanbuffer; /*f164 */ 14817 double sumatorio; 14818 SANE_Int gainmode; 14819 SANE_Int rst; 14820 14821 DBG (DBG_FNC, "> Calib_BlackShading_jkd(*myCalib)\n"); 14822 14823 memset (&myCalibTable, 0, sizeof (struct st_gain_offset)); 14824 for (C = CL_RED; C <= CL_BLUE; C++) 14825 { 14826 myCalibTable.pag[C] = 3; 14827 myCalibTable.vgag1[C] = 4; 14828 myCalibTable.vgag2[C] = 4; 14829 } 14830 14831 calibcfg = 14832 (struct st_calibration_config *) 14833 malloc (sizeof (struct st_calibration_config)); 14834 memset (calibcfg, 0x30, sizeof (struct st_calibration_config)); 14835 14836 myscancfg = (struct st_scanparams *) malloc (sizeof (struct st_scanparams)); 14837 memcpy (myscancfg, scancfg, sizeof (struct st_scanparams)); 14838 14839 myRegs = (SANE_Byte *) malloc (RT_BUFFER_LEN * sizeof (SANE_Byte)); 14840 memcpy (myRegs, Regs, RT_BUFFER_LEN * sizeof (SANE_Byte)); 14841 14842 Calib_LoadConfig (dev, calibcfg, scan.scantype, myscancfg->resolution_x, 14843 myscancfg->depth); 14844 gainmode = Lamp_GetGainMode (dev, myscancfg->resolution_x, scan.scantype); 14845 14846 Lamp_SetGainMode (dev, myRegs, myscancfg->resolution_x, gainmode); 14847 14848 rst = OK; 14849 14850 switch (scan.scantype) 14851 { 14852 case ST_NORMAL: 14853 /*a184 */ 14854 myscancfg->coord.left += scan.ser; 14855 myscancfg->coord.width &= 0xffff; 14856 break; 14857 case ST_TA: 14858 case ST_NEG: 14859 myscancfg->coord.left += scan.ser; 14860 break; 14861 } 14862 14863 /*a11b */ 14864 if ((myscancfg->coord.width & 1) != 0) 14865 myscancfg->coord.width++; 14866 14867 myscancfg->coord.top = 1; 14868 myscancfg->coord.height = calibcfg->BShadingHeight; 14869 14870 bytes_per_line = myscancfg->coord.width * 3; 14871 14872 /*a1e8 */ 14873 myscancfg->v157c = bytes_per_line; 14874 myscancfg->bytesperline = bytes_per_line; 14875 14876 scanbuffer = 14877 (SANE_Byte *) malloc (((myscancfg->coord.height + 16) * bytes_per_line) * 14878 sizeof (SANE_Byte)); 14879 if (scanbuffer == NULL) 14880 return ERROR; 14881 14882 /* Turn off lamp */ 14883 Lamp_Status_Set (dev, NULL, FALSE, FLB_LAMP); 14884 usleep (200 * 1000); 14885 14886 /* Scan image */ 14887 myCalib->shading_enabled = FALSE; 14888 rst = 14889 RTS_GetImage (dev, myRegs, myscancfg, &myCalibTable, scanbuffer, myCalib, 14890 0x101, gainmode); 14891 14892 /* Turn on lamp again */ 14893 if (scan.scantype != ST_NORMAL) 14894 { 14895 Lamp_Status_Set (dev, NULL, FALSE, TMA_LAMP); 14896 usleep (1000 * 1000); 14897 } 14898 else 14899 Lamp_Status_Set (dev, NULL, TRUE, FLB_LAMP); 14900 14901 if (rst != ERROR) 14902 { 14903 jkd_black = (SANE_Byte *) malloc (bytes_per_line); 14904 14905 if (jkd_black != NULL) 14906 { 14907 jkd_blackbpl = bytes_per_line; 14908 14909 for (x = 0; x < bytes_per_line; x++) 14910 { 14911 sumatorio = 0; 14912 14913 for (y = 0; y < myscancfg->coord.height + 16; y++) 14914 sumatorio += scanbuffer[x + (bytes_per_line * y)]; 14915 14916 sumatorio /= myscancfg->coord.height + 16; 14917 a = sumatorio; 14918 *(jkd_black + x) = _B0 (a); 14919 } 14920 } 14921 14922 /*if (RTS_Debug->SaveCalibFile != FALSE) */ 14923 { 14924 dbg_tiff_save ("blackshading_jkd.tiff", 14925 myscancfg->coord.width, 14926 myscancfg->coord.height, 14927 myscancfg->depth, 14928 CM_COLOR, 14929 myscancfg->resolution_x, 14930 myscancfg->resolution_y, 14931 scanbuffer, 14932 (myscancfg->coord.height + 16) * bytes_per_line); 14933 } 14934 } 14935 14936 free (scanbuffer); 14937 14938 return OK; 14939} 14940 14941static SANE_Int 14942Calib_test (struct st_device *dev, SANE_Byte * Regs, 14943 struct st_calibration *myCalib, struct st_scanparams *scancfg) 14944{ 14945 struct st_calibration_config *calibcfg; 14946 struct st_gain_offset myCalibTable; 14947 struct st_scanparams *myscancfg; 14948 SANE_Byte *myRegs; /*f1bc */ 14949 SANE_Int bytes_per_line; 14950 /**/ SANE_Int a, C; 14951 SANE_Byte *scanbuffer; /*f164 */ 14952 SANE_Int gainmode; 14953 SANE_Int rst; 14954 14955 DBG (DBG_FNC, "> Calib_test(*myCalib)\n"); 14956 14957 memset (&myCalibTable, 0, sizeof (struct st_gain_offset)); 14958 14959 calibcfg = 14960 (struct st_calibration_config *) 14961 malloc (sizeof (struct st_calibration_config)); 14962 memset (calibcfg, 0x30, sizeof (struct st_calibration_config)); 14963 14964 myscancfg = (struct st_scanparams *) malloc (sizeof (struct st_scanparams)); 14965 memcpy (myscancfg, scancfg, sizeof (struct st_scanparams)); 14966 14967 myRegs = (SANE_Byte *) malloc (RT_BUFFER_LEN * sizeof (SANE_Byte)); 14968 memcpy (myRegs, Regs, RT_BUFFER_LEN * sizeof (SANE_Byte)); 14969 14970 Calib_LoadConfig (dev, calibcfg, scan.scantype, myscancfg->resolution_x, 14971 myscancfg->depth); 14972 gainmode = Lamp_GetGainMode (dev, myscancfg->resolution_x, scan.scantype); 14973 14974 Lamp_SetGainMode (dev, myRegs, myscancfg->resolution_x, gainmode); 14975 14976 rst = OK; 14977 14978 switch (scan.scantype) 14979 { 14980 case ST_NORMAL: 14981 /*a184 */ 14982 myscancfg->coord.left += scan.ser; 14983 myscancfg->coord.width &= 0xffff; 14984 break; 14985 case ST_TA: 14986 case ST_NEG: 14987 myscancfg->coord.left += scan.ser; 14988 break; 14989 } 14990 14991 /*a11b */ 14992 if ((myscancfg->coord.width & 1) != 0) 14993 myscancfg->coord.width++; 14994 14995 myscancfg->coord.top = 100; 14996 myscancfg->coord.height = 30; 14997 14998 bytes_per_line = myscancfg->coord.width * 3; 14999 15000 /*a1e8 */ 15001 myscancfg->v157c = bytes_per_line; 15002 myscancfg->bytesperline = bytes_per_line; 15003 15004 scanbuffer = 15005 (SANE_Byte *) malloc (((myscancfg->coord.height + 16) * bytes_per_line) * 15006 sizeof (SANE_Byte)); 15007 if (scanbuffer == NULL) 15008 return ERROR; 15009 15010 /* Scan image */ 15011 myCalib->shading_enabled = FALSE; 15012 /*Head_Relocate(dev, dev->motorcfg->highspeedmotormove, MTR_FORWARD, 5500); */ 15013 15014 for (a = 0; a < 10; a++) 15015 { 15016 for (C = CL_RED; C <= CL_BLUE; C++) 15017 { 15018 myCalibTable.pag[C] = 3; 15019 myCalibTable.vgag1[C] = 4; 15020 myCalibTable.vgag2[C] = 4; 15021 myCalibTable.edcg1[C] = a * 20; 15022 } 15023 15024 Head_Relocate (dev, dev->motorcfg->highspeedmotormove, MTR_FORWARD, 15025 5000); 15026 rst = 15027 RTS_GetImage (dev, myRegs, myscancfg, &myCalibTable, scanbuffer, 15028 myCalib, 0x20000000, gainmode); 15029 Head_ParkHome (dev, TRUE, dev->motorcfg->parkhomemotormove); 15030 15031 if (rst != ERROR) 15032 { 15033 char name[30]; 15034 snprintf (name, 30, "calibtest-%i.tiff", a); 15035 dbg_tiff_save (name, 15036 myscancfg->coord.width, 15037 myscancfg->coord.height, 15038 myscancfg->depth, 15039 CM_COLOR, 15040 myscancfg->resolution_x, 15041 myscancfg->resolution_y, 15042 scanbuffer, 15043 (myscancfg->coord.height + 16) * bytes_per_line); 15044 } 15045 } 15046 15047 free (scanbuffer); 15048 15049 exit (0); 15050 return OK; 15051} 15052 15053static void 15054prueba (SANE_Byte * a) 15055{ 15056 /* SANE_Byte p[] = {}; */ 15057 /*int z = 69; */ 15058 15059 /*(a + 11) = 0x0; */ 15060 /*a[1] = a[1] | 0x40; */ 15061 15062 /*memcpy(a, &p, sizeof(p)); */ 15063 15064 /*memcpy(a + 0x12, p, 10); */ 15065 /*a[0x146] &= 0xdf; */ 15066 15067} 15068 15069void 15070shadingtest1 (struct st_device *dev, SANE_Byte * Regs, 15071 struct st_calibration *myCalib) 15072{ 15073 USHORT *buffer; 15074 int a; 15075 int bit[2]; 15076 15077 DBG (DBG_FNC, "+ shadingtest1(*Regs, *myCalib):\n"); 15078 15079 if ((Regs == NULL) || (myCalib == NULL)) 15080 return; 15081 15082 RTS_DMA_Reset (dev); 15083 15084 bit[0] = (Regs[0x60b] >> 6) & 1; 15085 bit[1] = (Regs[0x60b] >> 4) & 1; 15086 Regs[0x060b] &= 0xaf; 15087 15088 Write_Byte (dev->usb_handle, 0xee0b, Regs[0x060b]); 15089 15090 Regs[0x1cf] = 0; /* reset config. By default black shading disabled and pixel-rate */ 15091 /*Regs[0x1cf] |= 2; shadingbase 0x2000 */ 15092 Regs[0x1cf] |= 4; /* White shading enabled */ 15093 Regs[0x1cf] |= 0x20; /* 16 bits per channel */ 15094 15095 Write_Byte (dev->usb_handle, 0xe9cf, Regs[0x01cf]); 15096 15097 buffer = (USHORT *) malloc (sizeof (USHORT) * myCalib->shadinglength); 15098 15099 DBG (DBG_FNC, " -> shading length = %i\n", myCalib->shadinglength); 15100 15101 /* fill buffer */ 15102 for (a = 0; a < myCalib->shadinglength; a++) 15103 buffer[a] = RTS_Debug->shd + (a * 500); 15104 15105 for (a = 0; a < 3; a++) 15106 { 15107 RTS_DMA_Write (dev, a | 0x14, 0, 15108 sizeof (USHORT) * myCalib->shadinglength, 15109 (SANE_Byte *) buffer); 15110 } 15111 15112 data_bitset (&Regs[0x60b], 0x40, bit[0]); /*-x------*/ 15113 data_bitset (&Regs[0x60b], 0x10, bit[1]); /*---x----*/ 15114 15115 Write_Byte (dev->usb_handle, 0xee0b, Regs[0x060b]); 15116 15117 DBG (DBG_FNC, "- shadingtest1\n"); 15118} 15119 15120#endif 15121 15122#endif /* RTS8822_CORE */ 15123