shinkos6145: Major additions
* Remove S6145 fallback code if there is no library found. (Quality was very poor, and I'm not going to make a version for the S2245) * Remove most awareness of the S6145 correction data structure, and make the corrdata structure an opaque blob + len., and get rid of the extra padding. Except for what we need to pass in the print parameters. * Attach to the S2245 library if needed * S2245 library in the printing flow.
This commit is contained in:
parent
4c60edc0b7
commit
70a495eabb
47
README
47
README
|
@ -710,48 +710,45 @@
|
||||||
|
|
||||||
*** VERY IMPORTANT ***
|
*** VERY IMPORTANT ***
|
||||||
|
|
||||||
In order to generate usable output, the Sinfonia CHC-S6145 printer
|
In order to generate usable output, the Sinfonia CHC-S6145 and CHC-S2245
|
||||||
(and its siblings listed above) require the input data to be
|
printers (and their siblings listed above) require the input data to be
|
||||||
transformed using specific image processing algorithms.
|
transformed using specific image processing algorithms.
|
||||||
|
|
||||||
The library that implements this processing is dynamically loaded
|
The library that implements this processing is dynamically loaded
|
||||||
at runtime. There are three options:
|
at runtime. There are three options:
|
||||||
|
|
||||||
* libS6145ImageProcess -- Supported by Sinfonia, this is a proprietary
|
* libS6145ImageProcess and S2245IP -- Supported by Sinfonia, these
|
||||||
library only available for x86 and x86_64 linux targets. It can be
|
are proprietary libraries. They can be obtained by politely
|
||||||
obtained by politely contacting your local Sinfonia distributor.
|
contacting your local Sinfonia distributor.
|
||||||
|
|
||||||
If you have the appropriate permission fron Sinfonia and its
|
If you have the appropriate permission fron Sinfonia and their
|
||||||
technical and legal limitations are acceptible to you, we recommend
|
technical and legal limitations are acceptible to you, we
|
||||||
you use the supported libS6145ImageProcess library, as it will
|
recommend you use these official supported libraries.
|
||||||
generate the highest quality output.
|
|
||||||
|
|
||||||
* libS6145ImageReProcess -- GPL'd re-implementation of the Sinfonia
|
* libS6145ImageReProcess and libS2245ImageReProocess -- GPL'd
|
||||||
algorithms, available as source. It is a drop-in replacement
|
re-implementations of the Sinfonia algorithms, available as
|
||||||
that appears to generate identical output to the proprietary
|
source. They are drop-in replacement that appears to generate
|
||||||
Sinfonia library.
|
identical output to the proprietary Sinfonia libraries.
|
||||||
|
|
||||||
DISCLAIMER: Sinfonia Inc was not involved in the creation of
|
DISCLAIMER: Sinfonia Inc was not involved in the creation of
|
||||||
libS6145ImageReProcess and is not responsible in any way for any
|
these libraries and is not responsible in any way for any
|
||||||
deficiencies in its output. They will provide no support if it is
|
deficiencies in its output. They will provide no support if it is
|
||||||
used.
|
used.
|
||||||
|
|
||||||
Do *NOT* contact Sinfonia for support if you are using
|
Do *NOT* contact Sinfonia for support if you are using
|
||||||
libS6146ImageReProcess!
|
libS6146ImageReProcess or libS2245ImageReProcess!
|
||||||
|
|
||||||
(Please see the full disclaimer in libS6145ImageReProcess.c)
|
(Please see the full disclaimer in libS6145ImageReProcess.c and
|
||||||
|
libS2245ImageReProcess.c)
|
||||||
* If neither of the above libraries are found, the backend will
|
|
||||||
fall back to a very crude algorithm that generates low-quality
|
|
||||||
results not suitable for photographic output
|
|
||||||
|
|
||||||
As selphy_print is released under the terms of the GPL, it cannot
|
As selphy_print is released under the terms of the GPL, it cannot
|
||||||
normally be combined with proprietary libraries.
|
normally be combined with proprietary libraries.
|
||||||
|
|
||||||
Therefore, the authors of selphy_print grant its users an additional
|
Therefore, the authors of selphy_print grant its users an
|
||||||
permission (under section 7 of the GPLv3) to combine and/or redistribute
|
additional permission (under section 7 of the GPLv3) to combine
|
||||||
it with the libS6145ImageProcess library. For the full text of this
|
and/or redistribute it with the proprietart libS6145ImageProcess
|
||||||
license exception, please see the header of backend_shinkos6145.c
|
and/or S2245IP libraries. For the full text of this license
|
||||||
|
exception, please see the header of backend_shinkos6145.c
|
||||||
|
|
||||||
Valid commands:
|
Valid commands:
|
||||||
|
|
||||||
|
@ -1139,7 +1136,7 @@
|
||||||
DNP DS620 / DS620A (aka Citizen CX-02)
|
DNP DS620 / DS620A (aka Citizen CX-02)
|
||||||
DNP DS820 / DS820A (aka Citizen CX-02W)
|
DNP DS820 / DS820A (aka Citizen CX-02W)
|
||||||
DNP DS-RX1 / DNP DS-RX1HS (aka Citizen CY and CY-02)
|
DNP DS-RX1 / DNP DS-RX1HS (aka Citizen CY and CY-02)
|
||||||
DNP DS-QW410
|
DNP DS-QW410
|
||||||
|
|
||||||
Theoretically supported printers: (Untested)
|
Theoretically supported printers: (Untested)
|
||||||
|
|
||||||
|
|
|
@ -24,11 +24,11 @@
|
||||||
*
|
*
|
||||||
* An additional permission is granted, under the GPLv3 section 7, to combine
|
* An additional permission is granted, under the GPLv3 section 7, to combine
|
||||||
* and/or redistribute this program with the proprietary libS6145ImageProcess
|
* and/or redistribute this program with the proprietary libS6145ImageProcess
|
||||||
* library, providing you have *written permission* from Sinfonia Technology
|
* and S2245IP libraries, providing you have *written permission* from Sinfonia
|
||||||
* Co. LTD to use and/or redistribute that library.
|
* Technology Co. LTD to use and/or redistribute that library.
|
||||||
*
|
*
|
||||||
* You must still adhere to all other terms of the license to this program
|
* You must still adhere to all other terms of the license to this program
|
||||||
* (ie GPLv3) and the license of the libS6145ImageProcess library.
|
* (ie GPLv3) and the license of the libS6145ImageProcess/S2245IP libraries.
|
||||||
*
|
*
|
||||||
* SPDX-License-Identifier: GPL-3.0+ with special exception
|
* SPDX-License-Identifier: GPL-3.0+ with special exception
|
||||||
*
|
*
|
||||||
|
@ -40,6 +40,7 @@
|
||||||
#include "backend_sinfonia.h"
|
#include "backend_sinfonia.h"
|
||||||
|
|
||||||
#include <time.h>
|
#include <time.h>
|
||||||
|
#include <stdbool.h>
|
||||||
|
|
||||||
#ifndef WITH_DYNAMIC
|
#ifndef WITH_DYNAMIC
|
||||||
#warning "No dynamic loading support!"
|
#warning "No dynamic loading support!"
|
||||||
|
@ -49,8 +50,24 @@
|
||||||
typedef int (*ImageProcessingFN)(unsigned char *, unsigned short *, void *);
|
typedef int (*ImageProcessingFN)(unsigned char *, unsigned short *, void *);
|
||||||
typedef int (*ImageAvrCalcFN)(unsigned char *, unsigned short, unsigned short, unsigned char *);
|
typedef int (*ImageAvrCalcFN)(unsigned char *, unsigned short, unsigned short, unsigned char *);
|
||||||
|
|
||||||
#define LIB_NAME "libS6145ImageProcess" DLL_SUFFIX // Official library
|
#define LIB6145_NAME "libS6145ImageProcess" DLL_SUFFIX // Official library
|
||||||
#define LIB_NAME_RE "libS6145ImageReProcess" DLL_SUFFIX // Reimplemented library
|
#define LIB6145_NAME_RE "libS6145ImageReProcess" DLL_SUFFIX // Reimplemented library
|
||||||
|
|
||||||
|
#define S6145_CORRDATA_HEADDOTS_OFFSET 8834
|
||||||
|
#define S6145_CORRDATA_WIDTH_OFFSET 12432
|
||||||
|
#define S6145_CORRDATA_HEIGHT_OFFSET 12434
|
||||||
|
#define S6145_CORRDATA_EXTRA_LEN 4
|
||||||
|
|
||||||
|
|
||||||
|
typedef bool (*ip_imageProcFN)(uint16_t *destData, uint8_t *srcInRgb,
|
||||||
|
uint16_t width, uint16_t height, void *srcIpp);
|
||||||
|
typedef bool (*ip_checkIppFN)(uint16_t width, uint16_t height, void *srcIpp);
|
||||||
|
typedef bool (*ip_getMemorySizeFN)(uint32_t *szMemory,
|
||||||
|
uint16_t width, uint16_t height,
|
||||||
|
void *srcIpp);
|
||||||
|
|
||||||
|
#define LIB2245_NAME "libS2245ImageProcess" DLL_SUFFIX // Official library
|
||||||
|
#define LIB2245_NAME_RE "libS2245ImageReProcess" DLL_SUFFIX // Reimplemented library
|
||||||
|
|
||||||
enum {
|
enum {
|
||||||
S_IDLE = 0,
|
S_IDLE = 0,
|
||||||
|
@ -59,132 +76,6 @@ enum {
|
||||||
S_FINISHED,
|
S_FINISHED,
|
||||||
};
|
};
|
||||||
|
|
||||||
/* "Image Correction Parameter" File */
|
|
||||||
// 128 bytes total, apparently an array of 32-bit values
|
|
||||||
struct tankParamTable {
|
|
||||||
uint32_t trdTankSize;
|
|
||||||
uint32_t sndTankSize;
|
|
||||||
uint32_t fstTankSize;
|
|
||||||
uint32_t trdTankIniEnergy;
|
|
||||||
uint32_t sndTankIniEnergy;
|
|
||||||
uint32_t fstTankIniEnergy;
|
|
||||||
uint32_t trdTrdConductivity;
|
|
||||||
uint32_t sndSndConductivity;
|
|
||||||
uint32_t fstFstConductivity;
|
|
||||||
uint32_t outTrdConductivity;
|
|
||||||
uint32_t trdSndConductivity;
|
|
||||||
uint32_t sndFstConductivity;
|
|
||||||
uint32_t fstOutConductivity;
|
|
||||||
uint32_t plusMaxEnergy;
|
|
||||||
uint32_t minusMaxEnergy;
|
|
||||||
uint32_t plusMaxEnergyPreRead;
|
|
||||||
uint32_t minusMaxEnergyPreRead;
|
|
||||||
uint32_t preReadLevelDiff;
|
|
||||||
uint32_t rsvd[14]; // null?
|
|
||||||
} __attribute__((packed));
|
|
||||||
|
|
||||||
struct shinkos6145_correctionparam {
|
|
||||||
uint16_t pulseTransTable_Y[256]; // @0
|
|
||||||
uint16_t pulseTransTable_M[256]; // @512
|
|
||||||
uint16_t pulseTransTable_C[256]; // @1024
|
|
||||||
uint16_t pulseTransTable_O[256]; // @1536
|
|
||||||
|
|
||||||
uint16_t lineHistCoefTable_Y[256]; // @2048
|
|
||||||
uint16_t lineHistCoefTable_M[256]; // @2560
|
|
||||||
uint16_t lineHistCoefTable_C[256]; // @3072
|
|
||||||
uint16_t lineHistCoefTable_O[256]; // @3584
|
|
||||||
|
|
||||||
uint16_t lineCorrectEnvA_Y; // @4096
|
|
||||||
uint16_t lineCorrectEnvA_M; // @4098
|
|
||||||
uint16_t lineCorrectEnvA_C; // @4100
|
|
||||||
uint16_t lineCorrectEnvA_O; // @4102
|
|
||||||
|
|
||||||
uint16_t lineCorrectEnvB_Y; // @4104
|
|
||||||
uint16_t lineCorrectEnvB_M; // @4106
|
|
||||||
uint16_t lineCorrectEnvB_C; // @4108
|
|
||||||
uint16_t lineCorrectEnvB_O; // @4110
|
|
||||||
|
|
||||||
uint16_t lineCorrectEnvC_Y; // @4112
|
|
||||||
uint16_t lineCorrectEnvC_M; // @4114
|
|
||||||
uint16_t lineCorrectEnvC_C; // @4116
|
|
||||||
uint16_t lineCorrectEnvC_O; // @4118
|
|
||||||
|
|
||||||
uint32_t lineCorrectSlice_Y; // @4120
|
|
||||||
uint32_t lineCorrectSlice_M; // @4124
|
|
||||||
uint32_t lineCorrectSlice_C; // @4128
|
|
||||||
uint32_t lineCorrectSlice_O; // @4132
|
|
||||||
|
|
||||||
uint32_t lineCorrectSlice1Line_Y; // @4136
|
|
||||||
uint32_t lineCorrectSlice1Line_M; // @4140
|
|
||||||
uint32_t lineCorrectSlice1Line_C; // @4144
|
|
||||||
uint32_t lineCorrectSlice1Line_O; // @4148
|
|
||||||
|
|
||||||
uint32_t lineCorrectPulseMax_Y; // @4152 [array]
|
|
||||||
uint32_t lineCorrectPulseMax_M; // @4156 [array]
|
|
||||||
uint32_t lineCorrectPulseMax_C; // @4160 [array]
|
|
||||||
uint32_t lineCorrectPulseMax_O; // @4164 [array]
|
|
||||||
|
|
||||||
struct tankParamTable tableTankParam_Y; // @4168
|
|
||||||
struct tankParamTable tableTankParam_M; // @4296
|
|
||||||
struct tankParamTable tableTankParam_C; // @4424
|
|
||||||
struct tankParamTable tableTankParam_O; // @4552
|
|
||||||
|
|
||||||
uint16_t tankPlusMaxEnergyTable_Y[256]; // @4680
|
|
||||||
uint16_t tankPlusMaxEnergyTable_M[256]; // @5192
|
|
||||||
uint16_t tankPlusMaxEnergyTable_C[256]; // @5704
|
|
||||||
uint16_t tankPlusMaxEnergyTable_O[256]; // @6216
|
|
||||||
|
|
||||||
uint16_t tankMinusMaxEnergy_Y[256]; // @6728
|
|
||||||
uint16_t tankMinusMaxEnergy_M[256]; // @7240
|
|
||||||
uint16_t tankMinusMaxEnergy_C[256]; // @7752
|
|
||||||
uint16_t tankMinusMaxEnergy_O[256]; // @8264
|
|
||||||
|
|
||||||
uint16_t printMaxPulse_Y; // @8776
|
|
||||||
uint16_t printMaxPulse_M; // @8778
|
|
||||||
uint16_t printMaxPulse_C; // @8780
|
|
||||||
uint16_t printMaxPulse_O; // @8782
|
|
||||||
|
|
||||||
uint16_t mtfWeightH_Y; // @8784
|
|
||||||
uint16_t mtfWeightH_M; // @8786
|
|
||||||
uint16_t mtfWeightH_C; // @8788
|
|
||||||
uint16_t mtfWeightH_O; // @8790
|
|
||||||
|
|
||||||
uint16_t mtfWeightV_Y; // @8792
|
|
||||||
uint16_t mtfWeightV_M; // @8794
|
|
||||||
uint16_t mtfWeightV_C; // @8796
|
|
||||||
uint16_t mtfWeightV_O; // @8798
|
|
||||||
|
|
||||||
uint16_t mtfSlice_Y; // @8800
|
|
||||||
uint16_t mtfSlice_M; // @8802
|
|
||||||
uint16_t mtfSlice_C; // @8804
|
|
||||||
uint16_t mtfSlice_O; // @8806
|
|
||||||
|
|
||||||
uint16_t val_1; // @8808 // 1 enables linepreprintprocess
|
|
||||||
uint16_t val_2; // @8810 // 1 enables ctankprocess
|
|
||||||
uint16_t printOpLevel; // @8812
|
|
||||||
uint16_t matteMode; // @8814 // 1 for matte
|
|
||||||
|
|
||||||
uint16_t randomBase[4]; // @8816 [use lower byte of each]
|
|
||||||
|
|
||||||
uint16_t matteSize; // @8824
|
|
||||||
uint16_t matteGloss; // @8826
|
|
||||||
uint16_t matteDeglossBlk; // @8828
|
|
||||||
uint16_t matteDeglossWht; // @8830
|
|
||||||
|
|
||||||
uint16_t printSideOffset; // @8832
|
|
||||||
uint16_t headDots; // @8834 [always 0x0780, ie 1920. print width
|
|
||||||
|
|
||||||
uint16_t SideEdgeCoefTable[128]; // @8836
|
|
||||||
uint8_t rsvd_2[256]; // @9092, null?
|
|
||||||
uint16_t SideEdgeLvCoefTable[256]; // @9348
|
|
||||||
uint8_t rsvd_3[2572]; // @9860, null?
|
|
||||||
|
|
||||||
/* User-supplied data */
|
|
||||||
uint16_t width; // @12432
|
|
||||||
uint16_t height; // @12434
|
|
||||||
uint8_t pad[3948]; // @12436, null.
|
|
||||||
} __attribute__((packed)); /* 16384 bytes */
|
|
||||||
|
|
||||||
/* Structs for printer */
|
/* Structs for printer */
|
||||||
struct s6145_print_cmd {
|
struct s6145_print_cmd {
|
||||||
struct sinfonia_cmd_hdr hdr;
|
struct sinfonia_cmd_hdr hdr;
|
||||||
|
@ -738,7 +629,6 @@ struct s2245_imagecorr_resp {
|
||||||
uint32_t total_size;
|
uint32_t total_size;
|
||||||
} __attribute__((packed));
|
} __attribute__((packed));
|
||||||
|
|
||||||
|
|
||||||
struct s6145_imagecorr_data {
|
struct s6145_imagecorr_data {
|
||||||
uint8_t remain_pkt;
|
uint8_t remain_pkt;
|
||||||
uint8_t return_size; /* Always 0x10 */
|
uint8_t return_size; /* Always 0x10 */
|
||||||
|
@ -764,10 +654,15 @@ struct shinkos6145_ctx {
|
||||||
size_t eepromlen;
|
size_t eepromlen;
|
||||||
|
|
||||||
void *dl_handle;
|
void *dl_handle;
|
||||||
|
|
||||||
ImageProcessingFN ImageProcessing;
|
ImageProcessingFN ImageProcessing;
|
||||||
ImageAvrCalcFN ImageAvrCalc;
|
ImageAvrCalcFN ImageAvrCalc;
|
||||||
|
|
||||||
struct shinkos6145_correctionparam *corrdata;
|
ip_imageProcFN ip_imageProc;
|
||||||
|
ip_checkIppFN ip_checkIpp;
|
||||||
|
ip_getMemorySizeFN ip_getMemorySize;
|
||||||
|
|
||||||
|
void *corrdata; /* Correction table */
|
||||||
uint16_t corrdatalen;
|
uint16_t corrdatalen;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -944,7 +839,7 @@ static int shinkos6145_dump_corrdata(struct shinkos6145_ctx *ctx, char *fname)
|
||||||
return fd;
|
return fd;
|
||||||
}
|
}
|
||||||
|
|
||||||
ret = write(fd, ctx->corrdata, sizeof(struct shinkos6145_correctionparam));
|
ret = write(fd, ctx->corrdata, ctx->corrdatalen);
|
||||||
close(fd);
|
close(fd);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1011,13 +906,13 @@ static int shinkos6145_get_imagecorr(struct shinkos6145_ctx *ctx)
|
||||||
ctx->corrdatalen = le16_to_cpu(resp.total_size);
|
ctx->corrdatalen = le16_to_cpu(resp.total_size);
|
||||||
INFO("Fetching %u bytes of image correction data\n", ctx->corrdatalen);
|
INFO("Fetching %u bytes of image correction data\n", ctx->corrdatalen);
|
||||||
|
|
||||||
ctx->corrdata = malloc(sizeof(struct shinkos6145_correctionparam));
|
ctx->corrdata = malloc(ctx->corrdatalen + S6145_CORRDATA_EXTRA_LEN);
|
||||||
if (!ctx->corrdata) {
|
if (!ctx->corrdata) {
|
||||||
ERROR("Memory allocation failure\n");
|
ERROR("Memory allocation failure\n");
|
||||||
ret = CUPS_BACKEND_FAILED;
|
ret = CUPS_BACKEND_FAILED;
|
||||||
goto done;
|
goto done;
|
||||||
}
|
}
|
||||||
memset(ctx->corrdata, 0, sizeof(struct shinkos6145_correctionparam));
|
memset(ctx->corrdata, 0, ctx->corrdatalen);
|
||||||
total = 0;
|
total = 0;
|
||||||
|
|
||||||
while (total < ctx->corrdatalen) {
|
while (total < ctx->corrdatalen) {
|
||||||
|
@ -1036,15 +931,12 @@ static int shinkos6145_get_imagecorr(struct shinkos6145_ctx *ctx)
|
||||||
DEBUG("correction block transferred (%u/%u total)\n", total, ctx->corrdatalen);
|
DEBUG("correction block transferred (%u/%u total)\n", total, ctx->corrdatalen);
|
||||||
|
|
||||||
}
|
}
|
||||||
|
ctx->corrdatalen += S6145_CORRDATA_EXTRA_LEN;
|
||||||
|
|
||||||
done:
|
done:
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
// XXX this is bogus, corrdata is 10224 bytes vs the 12432 bytes of the S6145!
|
|
||||||
// However they use the same image processing DLL so the S2245 data must be
|
|
||||||
// transforamble somehow. Or is it?
|
|
||||||
static int shinkos2245_get_imagecorr(struct shinkos6145_ctx *ctx, uint8_t options)
|
static int shinkos2245_get_imagecorr(struct shinkos6145_ctx *ctx, uint8_t options)
|
||||||
{
|
{
|
||||||
struct s2245_imagecorr_req cmd;
|
struct s2245_imagecorr_req cmd;
|
||||||
|
@ -1055,7 +947,7 @@ static int shinkos2245_get_imagecorr(struct shinkos6145_ctx *ctx, uint8_t option
|
||||||
cmd.hdr.cmd = cpu_to_le16(SINFONIA_CMD_GETCORR);
|
cmd.hdr.cmd = cpu_to_le16(SINFONIA_CMD_GETCORR);
|
||||||
cmd.hdr.len = sizeof(cmd) - sizeof(cmd.hdr);
|
cmd.hdr.len = sizeof(cmd) - sizeof(cmd.hdr);
|
||||||
cmd.options = options;
|
cmd.options = options;
|
||||||
cmd.flags = S2245_IMAGECORR_FLAG_CONTOUR_ENH; // XXX make configurable?
|
cmd.flags = S2245_IMAGECORR_FLAG_CONTOUR_ENH; // XXX make configurable? or key off a flag in the job?
|
||||||
|
|
||||||
if (ctx->corrdata) {
|
if (ctx->corrdata) {
|
||||||
free(ctx->corrdata);
|
free(ctx->corrdata);
|
||||||
|
@ -1072,13 +964,13 @@ static int shinkos2245_get_imagecorr(struct shinkos6145_ctx *ctx, uint8_t option
|
||||||
ctx->corrdatalen = le16_to_cpu(resp.total_size);
|
ctx->corrdatalen = le16_to_cpu(resp.total_size);
|
||||||
INFO("Fetching %u bytes of image correction data\n", ctx->corrdatalen);
|
INFO("Fetching %u bytes of image correction data\n", ctx->corrdatalen);
|
||||||
|
|
||||||
ctx->corrdata = malloc(sizeof(struct shinkos6145_correctionparam));
|
ctx->corrdata = malloc(ctx->corrdatalen);
|
||||||
if (!ctx->corrdata) {
|
if (!ctx->corrdata) {
|
||||||
ERROR("Memory allocation failure\n");
|
ERROR("Memory allocation failure\n");
|
||||||
ret = CUPS_BACKEND_FAILED;
|
ret = CUPS_BACKEND_FAILED;
|
||||||
goto done;
|
goto done;
|
||||||
}
|
}
|
||||||
memset(ctx->corrdata, 0, sizeof(struct shinkos6145_correctionparam));
|
memset(ctx->corrdata, 0, ctx->corrdatalen);
|
||||||
total = 0;
|
total = 0;
|
||||||
|
|
||||||
while (total < ctx->corrdatalen) {
|
while (total < ctx->corrdatalen) {
|
||||||
|
@ -1098,12 +990,10 @@ static int shinkos2245_get_imagecorr(struct shinkos6145_ctx *ctx, uint8_t option
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
done:
|
done:
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
static int shinkos6145_get_eeprom(struct shinkos6145_ctx *ctx)
|
static int shinkos6145_get_eeprom(struct shinkos6145_ctx *ctx)
|
||||||
{
|
{
|
||||||
struct sinfonia_cmd_hdr cmd;
|
struct sinfonia_cmd_hdr cmd;
|
||||||
|
@ -1336,34 +1226,55 @@ static int shinkos6145_attach(void *vctx, struct libusb_device_handle *dev, int
|
||||||
ctx->dev.params = s2245_params;
|
ctx->dev.params = s2245_params;
|
||||||
ctx->dev.params_count = s2245_params_num;
|
ctx->dev.params_count = s2245_params_num;
|
||||||
ctx->dev.error_codes = &s2245_error_codes;
|
ctx->dev.error_codes = &s2245_error_codes;
|
||||||
|
|
||||||
|
#if defined(WITH_DYNAMIC)
|
||||||
|
INFO("Attempting to load image processing library\n");
|
||||||
|
ctx->dl_handle = DL_OPEN(LIB2245_NAME); /* Try the Sinfonia one first */
|
||||||
|
if (!ctx->dl_handle)
|
||||||
|
ctx->dl_handle = DL_OPEN(LIB2245_NAME_RE); /* Then the RE one */
|
||||||
|
if (ctx->dl_handle) {
|
||||||
|
ctx->ip_imageProc = DL_SYM(ctx->dl_handle, "ip_ImageProc");
|
||||||
|
ctx->ip_checkIpp = DL_SYM(ctx->dl_handle, "ip_checkIpp");
|
||||||
|
ctx->ip_getMemorySize = DL_SYM(ctx->dl_handle, "ip_getMemorySize");
|
||||||
|
if (!ctx->ip_imageProc || !ctx->ip_checkIpp || !ctx->ip_getMemorySize) {
|
||||||
|
WARNING("Problem resolving symbols in imaging processing library\n");
|
||||||
|
DL_CLOSE(ctx->dl_handle);
|
||||||
|
ctx->dl_handle = NULL;
|
||||||
|
} else {
|
||||||
|
INFO("Image processing library successfully loaded\n");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
#endif
|
||||||
} else if (type == P_SHINKO_S6145 ||
|
} else if (type == P_SHINKO_S6145 ||
|
||||||
type == P_SHINKO_S6145D) {
|
type == P_SHINKO_S6145D) {
|
||||||
ctx->dev.params = s6145_params;
|
ctx->dev.params = s6145_params;
|
||||||
ctx->dev.params_count = s6145_params_num;
|
ctx->dev.params_count = s6145_params_num;
|
||||||
ctx->dev.error_codes = &s6145_error_codes;
|
ctx->dev.error_codes = &s6145_error_codes;
|
||||||
|
|
||||||
|
#if defined(WITH_DYNAMIC)
|
||||||
|
INFO("Attempting to load image processing library\n");
|
||||||
|
ctx->dl_handle = DL_OPEN(LIB6145_NAME); /* Try the Sinfonia one first */
|
||||||
|
if (!ctx->dl_handle)
|
||||||
|
ctx->dl_handle = DL_OPEN(LIB6145_NAME_RE); /* Then the RE one */
|
||||||
|
if (ctx->dl_handle) {
|
||||||
|
ctx->ImageProcessing = DL_SYM(ctx->dl_handle, "ImageProcessing");
|
||||||
|
ctx->ImageAvrCalc = DL_SYM(ctx->dl_handle, "ImageAvrCalc");
|
||||||
|
if (!ctx->ImageProcessing || !ctx->ImageAvrCalc) {
|
||||||
|
WARNING("Problem resolving symbols in imaging processing library\n");
|
||||||
|
DL_CLOSE(ctx->dl_handle);
|
||||||
|
ctx->dl_handle = NULL;
|
||||||
|
} else {
|
||||||
|
INFO("Image processing library successfully loaded\n");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Attempt to open the library */
|
|
||||||
#if defined(WITH_DYNAMIC)
|
#if defined(WITH_DYNAMIC)
|
||||||
INFO("Attempting to load image processing library\n");
|
|
||||||
ctx->dl_handle = DL_OPEN(LIB_NAME); /* Try the Sinfonia one first */
|
|
||||||
if (!ctx->dl_handle)
|
if (!ctx->dl_handle)
|
||||||
ctx->dl_handle = DL_OPEN(LIB_NAME_RE); /* Then the RE one */
|
WARNING("Image processing library not found; will NOT be able to print!\n");
|
||||||
if (!ctx->dl_handle)
|
|
||||||
WARNING("Image processing library not found, using internal fallback code\n");
|
|
||||||
if (ctx->dl_handle) {
|
|
||||||
ctx->ImageProcessing = DL_SYM(ctx->dl_handle, "ImageProcessing");
|
|
||||||
ctx->ImageAvrCalc = DL_SYM(ctx->dl_handle, "ImageAvrCalc");
|
|
||||||
if (!ctx->ImageProcessing || !ctx->ImageAvrCalc) {
|
|
||||||
WARNING("Problem resolving symbols in imaging processing library\n");
|
|
||||||
DL_CLOSE(ctx->dl_handle);
|
|
||||||
ctx->dl_handle = NULL;
|
|
||||||
} else {
|
|
||||||
INFO("Image processing library successfully loaded\n");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
#else
|
#else
|
||||||
WARNING("Dynamic library support not enabled, using internal fallback code\n");
|
WARNING("Image processing library cannot be loaded; will NOT be able to print!e\n");
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
/* Ensure jobid is sane */
|
/* Ensure jobid is sane */
|
||||||
|
@ -1412,98 +1323,6 @@ static void shinkos6145_teardown(void *vctx) {
|
||||||
free(ctx);
|
free(ctx);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void lib6145_calc_avg(struct shinkos6145_ctx *ctx,
|
|
||||||
const struct sinfonia_printjob *job,
|
|
||||||
uint16_t rows, uint16_t cols)
|
|
||||||
{
|
|
||||||
uint32_t plane, i, planelen;
|
|
||||||
planelen = rows * cols;
|
|
||||||
|
|
||||||
for (plane = 0 ; plane < 3 ; plane++) {
|
|
||||||
uint64_t sum = 0;
|
|
||||||
|
|
||||||
for (i = 0 ; i < planelen ; i++) {
|
|
||||||
sum += job->databuf[(planelen * plane) + i];
|
|
||||||
}
|
|
||||||
ctx->image_avg[plane] = (sum / planelen);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
static void lib6145_process_image(uint8_t *src, uint16_t *dest,
|
|
||||||
struct shinkos6145_correctionparam *corrdata,
|
|
||||||
uint8_t oc_mode)
|
|
||||||
{
|
|
||||||
uint32_t in, out;
|
|
||||||
|
|
||||||
uint16_t pad_l, pad_r, row_lim;
|
|
||||||
uint16_t row, col;
|
|
||||||
|
|
||||||
row_lim = le16_to_cpu(corrdata->headDots);
|
|
||||||
pad_l = (row_lim - le16_to_cpu(corrdata->width)) / 2;
|
|
||||||
pad_r = pad_l + le16_to_cpu(corrdata->width);
|
|
||||||
out = 0;
|
|
||||||
in = 0;
|
|
||||||
|
|
||||||
/* Convert YMC 8-bit to 16-bit, and pad appropriately to full stripe */
|
|
||||||
for (row = 0 ; row < le16_to_cpu(corrdata->height) ; row++) {
|
|
||||||
for (col = 0 ; col < row_lim; col++) {
|
|
||||||
uint16_t val;
|
|
||||||
if (col < pad_l) {
|
|
||||||
val = 0;
|
|
||||||
} else if (col < pad_r) {
|
|
||||||
val = corrdata->pulseTransTable_Y[src[in++]];
|
|
||||||
} else {
|
|
||||||
val = 0;
|
|
||||||
}
|
|
||||||
dest[out++] = val;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
for (row = 0 ; row < le16_to_cpu(corrdata->height) ; row++) {
|
|
||||||
for (col = 0 ; col < row_lim; col++) {
|
|
||||||
uint16_t val;
|
|
||||||
if (col < pad_l) {
|
|
||||||
val = 0;
|
|
||||||
} else if (col < pad_r) {
|
|
||||||
val = corrdata->pulseTransTable_M[src[in++]];
|
|
||||||
} else {
|
|
||||||
val = 0;
|
|
||||||
}
|
|
||||||
dest[out++] = val;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
for (row = 0 ; row < le16_to_cpu(corrdata->height) ; row++) {
|
|
||||||
for (col = 0 ; col < row_lim; col++) {
|
|
||||||
uint16_t val;
|
|
||||||
if (col < pad_l) {
|
|
||||||
val = 0;
|
|
||||||
} else if (col < pad_r) {
|
|
||||||
val = corrdata->pulseTransTable_C[src[in++]];
|
|
||||||
} else {
|
|
||||||
val = 0;
|
|
||||||
}
|
|
||||||
dest[out++] = val;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Generate lamination plane, if desired */
|
|
||||||
if (oc_mode > PRINT_MODE_NO_OC) {
|
|
||||||
// XXX matters if we're using glossy/matte...
|
|
||||||
for (row = 0 ; row < le16_to_cpu(corrdata->height) ; row++) {
|
|
||||||
for (col = 0 ; col < row_lim; col++) {
|
|
||||||
uint16_t val;
|
|
||||||
if (col < pad_l) {
|
|
||||||
val = 0;
|
|
||||||
} else if (col < pad_r) {
|
|
||||||
val = corrdata->pulseTransTable_O[corrdata->printOpLevel];
|
|
||||||
} else {
|
|
||||||
val = 0;
|
|
||||||
}
|
|
||||||
dest[out++] = val;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
static int shinkos6145_read_parse(void *vctx, const void **vjob, int data_fd, int copies) {
|
static int shinkos6145_read_parse(void *vctx, const void **vjob, int data_fd, int copies) {
|
||||||
struct shinkos6145_ctx *ctx = vctx;
|
struct shinkos6145_ctx *ctx = vctx;
|
||||||
struct sinfonia_printjob *job = NULL;
|
struct sinfonia_printjob *job = NULL;
|
||||||
|
@ -1850,39 +1669,69 @@ top:
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Set up library transform... */
|
if (ctx->dev.type == P_SHINKO_S2245) {
|
||||||
uint32_t newlen = le16_to_cpu(ctx->corrdata->headDots) *
|
uint32_t bufSize = 0;
|
||||||
job->jp.rows * sizeof(uint16_t) * 4;
|
uint16_t *newbuf;
|
||||||
uint16_t *databuf2 = malloc(newlen);
|
|
||||||
|
|
||||||
/* Set the size in the correctiondata */
|
if (!ctx->ip_checkIpp(job->jp.columns, job->jp.rows, ctx->corrdata)) {
|
||||||
ctx->corrdata->width = cpu_to_le16(job->jp.columns);
|
ERROR("ip_checkIPP Failed!\n");
|
||||||
ctx->corrdata->height = cpu_to_le16(job->jp.rows);
|
|
||||||
|
|
||||||
|
|
||||||
/* Perform the actual library transform */
|
|
||||||
if (ctx->dl_handle) {
|
|
||||||
INFO("Calling image processing library...\n");
|
|
||||||
|
|
||||||
if (ctx->ImageAvrCalc(job->databuf, job->jp.columns, job->jp.rows, ctx->image_avg)) {
|
|
||||||
free(databuf2);
|
|
||||||
ERROR("Library returned error!\n");
|
|
||||||
return CUPS_BACKEND_FAILED;
|
return CUPS_BACKEND_FAILED;
|
||||||
}
|
}
|
||||||
ctx->ImageProcessing(job->databuf, databuf2, ctx->corrdata);
|
if (!ctx->ip_getMemorySize(&bufSize, job->jp.columns, job->jp.rows, ctx->corrdata)) {
|
||||||
|
ERROR("ip_getMemorySize Failed!\n");
|
||||||
|
return CUPS_BACKEND_FAILED;
|
||||||
|
}
|
||||||
|
newbuf = malloc(bufSize);
|
||||||
|
if (!newbuf) {
|
||||||
|
ERROR("Memory Allocation failure!\n");
|
||||||
|
return CUPS_BACKEND_RETRY;
|
||||||
|
}
|
||||||
|
if (ctx->ip_imageProc(newbuf, job->databuf, job->jp.columns, job->jp.rows, ctx->corrdata)) {
|
||||||
|
ERROR("ip_imageProc Failed!\n");
|
||||||
|
free(newbuf);
|
||||||
|
return CUPS_BACKEND_FAILED;
|
||||||
|
}
|
||||||
|
free(job->databuf);
|
||||||
|
job->databuf = (uint8_t*)newbuf;
|
||||||
|
job->datalen = bufSize;
|
||||||
} else {
|
} else {
|
||||||
WARNING("Utilizing fallback internal image processing code\n");
|
uint16_t tmp;
|
||||||
WARNING(" *** Output quality will be poor! *** \n");
|
memcpy(&tmp, (uint8_t*)ctx->corrdata + S6145_CORRDATA_HEADDOTS_OFFSET, sizeof(tmp));
|
||||||
|
tmp = le16_to_cpu(tmp);
|
||||||
|
|
||||||
lib6145_calc_avg(ctx, job, job->jp.columns, job->jp.rows);
|
/* Set up library transform... */
|
||||||
lib6145_process_image(job->databuf, databuf2, ctx->corrdata, oc_mode);
|
uint32_t newlen = tmp * job->jp.rows * sizeof(uint16_t) * 4;
|
||||||
|
uint16_t *databuf2 = malloc(newlen);
|
||||||
|
if (!databuf2) {
|
||||||
|
ERROR("Memory Allocation failure!\n");
|
||||||
|
return CUPS_BACKEND_RETRY;
|
||||||
|
}
|
||||||
|
/* Set the size in the correctiondata */
|
||||||
|
tmp = cpu_to_le16(job->jp.columns);
|
||||||
|
memcpy((uint8_t*)ctx->corrdata + S6145_CORRDATA_WIDTH_OFFSET, &tmp, sizeof(tmp));
|
||||||
|
tmp = cpu_to_le16(job->jp.rows);
|
||||||
|
memcpy((uint8_t*)ctx->corrdata + S6145_CORRDATA_HEIGHT_OFFSET, &tmp, sizeof(tmp));
|
||||||
|
|
||||||
|
/* Perform the actual library transform */
|
||||||
|
if (ctx->dl_handle) {
|
||||||
|
INFO("Calling image processing library...\n");
|
||||||
|
|
||||||
|
if (ctx->ImageAvrCalc(job->databuf, job->jp.columns, job->jp.rows, ctx->image_avg)) {
|
||||||
|
free(databuf2);
|
||||||
|
ERROR("Library returned error!\n");
|
||||||
|
return CUPS_BACKEND_FAILED;
|
||||||
|
}
|
||||||
|
ctx->ImageProcessing(job->databuf, databuf2, ctx->corrdata);
|
||||||
|
} else {
|
||||||
|
ERROR("Image processing library not found! Cannot print!\n");
|
||||||
|
return CUPS_BACKEND_FAILED;
|
||||||
|
}
|
||||||
|
|
||||||
|
free(job->databuf);
|
||||||
|
job->databuf = (uint8_t*) databuf2;
|
||||||
|
job->datalen = newlen;
|
||||||
}
|
}
|
||||||
|
|
||||||
free(job->databuf);
|
|
||||||
job->databuf = (uint8_t*) databuf2;
|
|
||||||
job->datalen = newlen;
|
|
||||||
|
|
||||||
|
|
||||||
INFO("Sending print job (internal id %u)\n", ctx->jobid);
|
INFO("Sending print job (internal id %u)\n", ctx->jobid);
|
||||||
|
|
||||||
if (ctx->dev.type != P_SHINKO_S2245) {
|
if (ctx->dev.type != P_SHINKO_S2245) {
|
||||||
|
@ -1924,7 +1773,7 @@ top:
|
||||||
print.options |= 0x08;
|
print.options |= 0x08;
|
||||||
print.media = 0; /* ignore job->jp.media! */
|
print.media = 0; /* ignore job->jp.media! */
|
||||||
|
|
||||||
print.ipp = SINFONIA_PRINT28_IPP_CONTOUR;
|
print.ipp = SINFONIA_PRINT28_IPP_CONTOUR; // XXX make configurable?
|
||||||
print.method = cpu_to_le32(job->jp.method | SINFONIA_PRINT28_METHOD_ERR_RECOVERY | SINFONIA_PRINT28_METHOD_ERR_PREHEAT);
|
print.method = cpu_to_le32(job->jp.method | SINFONIA_PRINT28_METHOD_ERR_RECOVERY | SINFONIA_PRINT28_METHOD_ERR_PREHEAT);
|
||||||
|
|
||||||
if ((ret = sinfonia_docmd(&ctx->dev,
|
if ((ret = sinfonia_docmd(&ctx->dev,
|
||||||
|
@ -2140,7 +1989,7 @@ static const char *shinkos6145_prefixes[] = {
|
||||||
|
|
||||||
struct dyesub_backend shinkos6145_backend = {
|
struct dyesub_backend shinkos6145_backend = {
|
||||||
.name = "Shinko/Sinfonia CHC-S6145/CS2/S2245/S3",
|
.name = "Shinko/Sinfonia CHC-S6145/CS2/S2245/S3",
|
||||||
.version = "0.40" " (lib " LIBSINFONIA_VER ")",
|
.version = "0.41" " (lib " LIBSINFONIA_VER ")",
|
||||||
.uri_prefixes = shinkos6145_prefixes,
|
.uri_prefixes = shinkos6145_prefixes,
|
||||||
.cmdline_usage = shinkos6145_cmdline,
|
.cmdline_usage = shinkos6145_cmdline,
|
||||||
.cmdline_arg = shinkos6145_cmdline_arg,
|
.cmdline_arg = shinkos6145_cmdline_arg,
|
||||||
|
|
Loading…
Reference in New Issue