summaryrefslogtreecommitdiff
path: root/src/cups
diff options
context:
space:
mode:
authorDidier Raboud <odyx@debian.org>2014-05-27 08:45:14 +0200
committerDidier Raboud <odyx@debian.org>2014-05-27 08:45:14 +0200
commit58b4abe145a14a936e420a3ba5b7d0c6c56fa839 (patch)
tree04ab7e73f48fb25c9a927056402b680255d87687 /src/cups
parent68062125a3214a6262bb1899b81f93abb35c8be9 (diff)
Imported Upstream version 5.2.10
Diffstat (limited to 'src/cups')
-rw-r--r--src/cups/Makefile.am6
-rw-r--r--src/cups/Makefile.in4
-rw-r--r--src/cups/backend_common.c242
-rw-r--r--src/cups/blacklist11
-rw-r--r--src/cups/mitsu70x_print.c157
-rw-r--r--src/cups/selphy_print.c99
6 files changed, 371 insertions, 148 deletions
diff --git a/src/cups/Makefile.am b/src/cups/Makefile.am
index 939f1a8..ec2e01d 100644
--- a/src/cups/Makefile.am
+++ b/src/cups/Makefile.am
@@ -1,4 +1,4 @@
-## $Id: Makefile.am,v 1.146 2014/02/19 12:26:43 speachy Exp $
+## $Id: Makefile.am,v 1.148 2014/03/27 22:37:09 speachy Exp $
## Copyright (C) 2000 Roger Leigh
##
## This program is free software; you can redistribute it and/or modify
@@ -93,8 +93,8 @@ endif
## See http://www.cups.org/documentation.php/doc-1.6/man-backend.html
if BUILD_LIBUSB_BACKENDS
install-exec-hook:
+ chmod 700 $(DESTDIR)$(pkglibdir)/backend/backend_gutenprint
mv $(DESTDIR)$(pkglibdir)/backend/backend_gutenprint "$(DESTDIR)$(pkglibdir)/backend/gutenprint$(GUTENPRINT_MAJOR_VERSION)$(GUTENPRINT_MINOR_VERSION)+usb"
- chmod 700 "$(DESTDIR)$(pkglibdir)/backend/gutenprint$(GUTENPRINT_MAJOR_VERSION)$(GUTENPRINT_MINOR_VERSION)+usb"
endif
TESTS= test-ppds test-rastertogutenprint
@@ -118,7 +118,7 @@ if BUILD_LIBUSB_BACKENDS
backend_gutenprint_SOURCES = selphy_print.c kodak1400_print.c kodak6800_print.c kodak605_print.c shinko_s2145_print.c sony_updr150_print.c dnpds40_print.c mitsu70x_print.c backend_common.c backend_common.h
backend_gutenprint_LDADD = $(LIBUSB_LIBS)
-backend_gutenprint_CPPFLAGS = $(LIBUSB_CFLAGS) -DURI_PREFIX=\"gutenprint$(GUTENPRINT_MAJOR_VERSION)$(GUTENPRINT_MINOR_VERSION)+usb\"
+backend_gutenprint_CPPFLAGS = $(LIBUSB_CFLAGS) -DURI_PREFIX=\"gutenprint$(GUTENPRINT_MAJOR_VERSION)$(GUTENPRINT_MINOR_VERSION)+usb\" -DLIBUSB_PRE_1_0_10
endif
cups_genppd_@GUTENPRINT_RELEASE_VERSION@_SOURCES = genppd.c i18n.c i18n.h
diff --git a/src/cups/Makefile.in b/src/cups/Makefile.in
index 8af0f4a..25bfd1a 100644
--- a/src/cups/Makefile.in
+++ b/src/cups/Makefile.in
@@ -718,7 +718,7 @@ commandtoepson_SOURCES = commandtoepson.c
commandtoepson_LDADD = $(CUPS_LIBS)
@BUILD_LIBUSB_BACKENDS_TRUE@backend_gutenprint_SOURCES = selphy_print.c kodak1400_print.c kodak6800_print.c kodak605_print.c shinko_s2145_print.c sony_updr150_print.c dnpds40_print.c mitsu70x_print.c backend_common.c backend_common.h
@BUILD_LIBUSB_BACKENDS_TRUE@backend_gutenprint_LDADD = $(LIBUSB_LIBS)
-@BUILD_LIBUSB_BACKENDS_TRUE@backend_gutenprint_CPPFLAGS = $(LIBUSB_CFLAGS) -DURI_PREFIX=\"gutenprint$(GUTENPRINT_MAJOR_VERSION)$(GUTENPRINT_MINOR_VERSION)+usb\"
+@BUILD_LIBUSB_BACKENDS_TRUE@backend_gutenprint_CPPFLAGS = $(LIBUSB_CFLAGS) -DURI_PREFIX=\"gutenprint$(GUTENPRINT_MAJOR_VERSION)$(GUTENPRINT_MINOR_VERSION)+usb\" -DLIBUSB_PRE_1_0_10
cups_genppd_@GUTENPRINT_RELEASE_VERSION@_SOURCES = genppd.c i18n.c i18n.h
cups_genppd_@GUTENPRINT_RELEASE_VERSION@_CFLAGS = -DALL_LINGUAS='"$(ALL_LINGUAS)"' $(BUILD_SIMPLE_PPDS) $(TRANSLATE_PPDS)
cups_genppd_@GUTENPRINT_RELEASE_VERSION@_LDADD = $(CUPS_LIBS) $(GENPPD_LIBS) $(GUTENPRINT_LIBS) @LIBICONV@
@@ -1807,8 +1807,8 @@ $(top_builddir)/src/gutenprintui2/libgutenprintui2.la:
$(MAKE)
@BUILD_CUPS_TRUE@@BUILD_LIBUSB_BACKENDS_TRUE@install-exec-hook:
+@BUILD_CUPS_TRUE@@BUILD_LIBUSB_BACKENDS_TRUE@ chmod 700 $(DESTDIR)$(pkglibdir)/backend/backend_gutenprint
@BUILD_CUPS_TRUE@@BUILD_LIBUSB_BACKENDS_TRUE@ mv $(DESTDIR)$(pkglibdir)/backend/backend_gutenprint "$(DESTDIR)$(pkglibdir)/backend/gutenprint$(GUTENPRINT_MAJOR_VERSION)$(GUTENPRINT_MINOR_VERSION)+usb"
-@BUILD_CUPS_TRUE@@BUILD_LIBUSB_BACKENDS_TRUE@ chmod 700 "$(DESTDIR)$(pkglibdir)/backend/gutenprint$(GUTENPRINT_MAJOR_VERSION)$(GUTENPRINT_MINOR_VERSION)+usb"
@BUILD_LIBUSB_BACKENDS_TRUE@install-blacklist:
@BUILD_LIBUSB_BACKENDS_TRUE@ $(mkdir_p) $(DESTDIR)$(cupsdata_blacklistdir)
@BUILD_LIBUSB_BACKENDS_TRUE@ $(INSTALL_DATA) $(srcdir)/blacklist $(DESTDIR)$(cupsdata_blacklistdir)/net.sf.gimp-print.usb-quirks
diff --git a/src/cups/backend_common.c b/src/cups/backend_common.c
index 1139e12..73c6dba 100644
--- a/src/cups/backend_common.c
+++ b/src/cups/backend_common.c
@@ -27,7 +27,7 @@
#include "backend_common.h"
-#define BACKEND_VERSION "0.42G"
+#define BACKEND_VERSION "0.48G"
#ifndef URI_PREFIX
#error "Must Define URI_PREFIX"
#endif
@@ -91,6 +91,76 @@ done:
return buf;
}
+/* Used with the IEEE1284 deviceid string parsing */
+
+struct deviceid_dict {
+ char *key;
+ char *val;
+};
+
+#define MAX_DICT 32
+
+static int parse1284_data(const char *device_id, struct deviceid_dict* dict)
+{
+ char *ptr;
+ char key[256];
+ char val[256];
+ int num = 0;
+
+ //[whitespace]key[whitespace]:[whitespace]value[whitespace];
+ while (*device_id && num < MAX_DICT) {
+ /* Skip leading spaces */
+ if (*device_id == ' ')
+ device_id++;
+ if (!*device_id)
+ break;
+
+ /* Work out key */
+ for (ptr = key; *device_id && *device_id != ':'; device_id++)
+ *ptr++ = *device_id;
+ if (!*device_id)
+ break;
+ while (ptr > key && *(ptr-1) == ' ')
+ ptr--;
+ *ptr = 0;
+ device_id++;
+ if (!*device_id)
+ break;
+
+ /* Next up, value */
+ for (ptr = val; *device_id && *device_id != ';'; device_id++)
+ *ptr++ = *device_id;
+ if (!*device_id)
+ break;
+ while (ptr > val && *(ptr-1) == ' ')
+ ptr--;
+ *ptr = 0;
+ device_id++;
+
+ /* Add it to the dictionary */
+ dict[num].key = strdup(key);
+ dict[num].val = strdup(val);
+ num++;
+
+ if (!*device_id)
+ break;
+ }
+ return num;
+};
+
+static char *dict_find(const char *key, int dlen, struct deviceid_dict* dict)
+{
+ while(dlen) {
+ if (!strcmp(key, dict->key))
+ return dict->val;
+ dlen--;
+ dict++;
+ }
+ return NULL;
+}
+
+/* I/O functions */
+
int read_data(struct libusb_device_handle *dev, uint8_t endp,
uint8_t *buf, int buflen, int *readlen)
{
@@ -110,7 +180,7 @@ int read_data(struct libusb_device_handle *dev, uint8_t endp,
goto done;
}
- if (dyesub_debug) {
+ if (dyesub_debug > 1) {
int i;
DEBUG("<- ");
for (i = 0 ; i < *readlen; i++) {
@@ -138,10 +208,10 @@ int send_data(struct libusb_device_handle *dev, uint8_t endp,
buf, len2,
&num, 15000);
- if (dyesub_debug) {
+ if (dyesub_debug > 1) {
int i;
DEBUG("-> ");
- for (i = 0 ; i < len2; i++) {
+ for (i = 0 ; i < num; i++) {
DEBUG2("%02x ", *(buf+i));
}
DEBUG2("\n");
@@ -158,6 +228,7 @@ int send_data(struct libusb_device_handle *dev, uint8_t endp,
return 0;
}
+/* More stuff */
int terminate = 0;
static void sigterm_handler(int signum) {
@@ -237,9 +308,12 @@ static int print_scan_output(struct libusb_device *device,
struct dyesub_backend *backend)
{
struct libusb_device_handle *dev;
-
char buf[256];
- char *product = NULL, *serial = NULL, *manuf = NULL;
+ char *product = NULL, *serial = NULL, *manuf = NULL, *descr = NULL;
+
+ int dlen = 0;
+ struct deviceid_dict dict[MAX_DICT];
+ char *ieee_id;
if (libusb_open(device, &dev)) {
ERROR("Could not open device %04x:%04x (need to be root?)\n", desc->idVendor, desc->idProduct);
@@ -247,25 +321,77 @@ static int print_scan_output(struct libusb_device *device,
goto abort;
}
- /* Query detailed info */
- if (desc->iManufacturer) {
+ ieee_id = get_device_id(dev);
+
+ /* Get IEEE1284 info */
+ dlen = parse1284_data(ieee_id, dict);
+
+ /* Look up mfg string. */
+ if (manuf2 && strlen(manuf2)) {
+ manuf = url_encode(manuf2); /* Backend supplied */
+ } else if ((manuf = dict_find("MANUFACTURER", dlen, dict))) {
+ manuf = url_encode(manuf);
+ } else if ((manuf = dict_find("MFG", dlen, dict))) {
+ manuf = url_encode(manuf);
+ } else if ((manuf = dict_find("MFR", dlen, dict))) {
+ manuf = url_encode(manuf);
+ } else if (desc->iManufacturer) { /* Get from USB descriptor */
+ buf[0] = 0;
libusb_get_string_descriptor_ascii(dev, desc->iManufacturer, (unsigned char*)buf, STR_LEN_MAX);
sanitize_string(buf);
manuf = url_encode(buf);
}
- buf[0] = 0;
- if (desc->iProduct) {
- libusb_get_string_descriptor_ascii(dev, desc->iProduct, (unsigned char *)buf, STR_LEN_MAX);
+ if (!manuf || !strlen(manuf)) { /* Last-ditch */
+ if (manuf) free(manuf);
+ manuf = url_encode("Unknown");
+ }
+
+ /* Look up model number */
+ if ((product = dict_find("MODEL", dlen, dict))) {
+ product = url_encode(product);
+ } else if ((product = dict_find("MDL", dlen, dict))) {
+ product = url_encode(product);
+ } else if (desc->iProduct) { /* Get from USB descriptor */
+ buf[0] = 0;
+ libusb_get_string_descriptor_ascii(dev, desc->iProduct, (unsigned char*)buf, STR_LEN_MAX);
sanitize_string(buf);
product = url_encode(buf);
}
- buf[0] = 0;
- if (desc->iSerialNumber) {
+
+ if (!product || !strlen(product)) { /* Last-ditch */
+ if (!product) free(product);
+ product = url_encode("Unknown");
+ }
+
+ /* Look up description */
+ if ((descr = dict_find("DESCRIPTION", dlen, dict))) {
+ descr = strdup(descr);
+ } else if ((descr = dict_find("DES", dlen, dict))) {
+ descr = strdup(descr);
+ }
+ if (!descr || !strlen(descr)) { /* Last-ditch, generate */
+ char *product2 = url_decode(product);
+ char *manuf3 = url_decode(manuf);
+ descr = malloc(256);
+ sprintf(descr, "%s %s", manuf3, product2);
+ free(product2);
+ free(manuf3);
+ }
+
+ /* Look up serial number */
+ if ((serial = dict_find("SERIALNUMBER", dlen, dict))) {
+ serial = url_encode(serial);
+ } else if ((serial = dict_find("SN", dlen, dict))) {
+ serial = url_encode(serial);
+ } else if ((serial = dict_find("SER", dlen, dict))) {
+ serial = url_encode(serial);
+ } else if ((serial = dict_find("SERN", dlen, dict))) {
+ serial = url_encode(serial);
+ } else if (desc->iSerialNumber) { /* Get from USB descriptor */
libusb_get_string_descriptor_ascii(dev, desc->iSerialNumber, (unsigned char*)buf, STR_LEN_MAX);
sanitize_string(buf);
- } else if (backend->query_serno) {
- /* XXX this is ... a cut-n-paste hack */
-
+ serial = url_encode(buf);
+ } else if (backend->query_serno) { /* Get from backend hook */
int iface = 0;
struct libusb_config_descriptor *config;
@@ -274,6 +400,7 @@ static int print_scan_output(struct libusb_device *device,
/* If we fail to claim the printer, it's already in use
so we should just skip over it... */
+ buf[0] = 0;
if (!libusb_claim_interface(dev, iface)) {
int i;
uint8_t endp_up, endp_down;
@@ -291,15 +418,15 @@ static int print_scan_output(struct libusb_device *device,
backend->query_serno(dev, endp_up, endp_down, buf, STR_LEN_MAX);
libusb_release_interface(dev, iface);
}
+ serial = url_encode(buf);
}
-
- if (!strlen(buf)) {
+
+ if (!serial || !strlen(serial)) { /* Last-ditch */
+ if (serial) free(serial);
WARNING("**** THIS PRINTER DOES NOT REPORT A SERIAL NUMBER!\n");
- WARNING("**** If you intend to use multiple printers of this typpe, you\n");
+ WARNING("**** If you intend to use multiple printers of this type, you\n");
WARNING("**** must only plug one in at a time or unexpected behaivor will occur!\n");
serial = strdup("NONE_UNKNOWN");
- } else {
- serial = url_encode(buf);
}
if (dyesub_debug)
@@ -308,31 +435,23 @@ static int print_scan_output(struct libusb_device *device,
desc->idVendor, desc->idProduct, manuf, product, serial);
if (scan_only) {
- int j = 0, k = 0;
- char *ieee_id = get_device_id(dev);
- char *product2 = url_decode(product);
+ int k = 0;
/* URLify the manuf and model strings */
- if (strlen(manuf2))
- strncpy(buf, manuf2, sizeof(buf) - 2);
- else
- strncpy(buf, manuf, sizeof(buf) - 2);
+ strncpy(buf, manuf, sizeof(buf) - 2);
k = strlen(buf);
buf[k++] = '/';
buf[k] = 0;
- j = (manuf2 && strlen(manuf2)) ? strlen(manuf2) + 1 : 0;
- strncpy(buf + k, product + j, sizeof(buf)-k);
-
+ strncpy(buf + k, product, sizeof(buf)-k);
+
fprintf(stdout, "direct %s://%s?serial=%s&backend=%s \"%s\" \"%s\" \"%s\" \"\"\n",
prefix, buf, serial, backend->uri_prefix,
- product2, product2,
+ descr, descr,
ieee_id? ieee_id : "");
if (ieee_id)
free(ieee_id);
- if (product2)
- free(product2);
}
/* If a serial number was passed down, use it. */
@@ -344,10 +463,17 @@ static int print_scan_output(struct libusb_device *device,
if(serial) free(serial);
if(manuf) free(manuf);
if(product) free(product);
+ if(descr) free(descr);
libusb_close(dev);
abort:
+ /* Clean up the dictionary */
+ while (dlen--) {
+ free (dict[dlen].key);
+ free (dict[dlen].val);
+ }
+
return found;
}
@@ -381,7 +507,7 @@ static int find_and_enumerate(struct libusb_context *ctx,
struct libusb_device_descriptor desc;
int match = 0;
libusb_get_device_descriptor((*list)[i], &desc);
-
+
for (k = 0 ; backends[k] ; k++) {
if (backend && backend != backends[k])
continue;
@@ -464,7 +590,7 @@ for more details.\n\
You should have received a copy of the GNU General Public License\n\
along with this program; if not, write to the Free Software\n\
Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.\n\
-\n [http://www.gnu.org/licenses/gpl-2.0.html]\n\n";
+\n [http://www.gnu.org/licenses/gpl-3.0.html]\n\n";
fprintf(stderr, "%s", license);
}
@@ -473,6 +599,7 @@ static void print_help(char *argv0, struct dyesub_backend *backend)
{
struct libusb_context *ctx = NULL;
struct libusb_device **list = NULL;
+ int i;
char *ptr = strrchr(argv0, '/');
if (ptr)
@@ -490,9 +617,11 @@ static void print_help(char *argv0, struct dyesub_backend *backend)
DEBUG("\n");
DEBUG("Standalone Usage:\n");
DEBUG("\t%s\n", URI_PREFIX);
- DEBUG(" [ -D ] [ -G ] [ -S serialnum ] [ -B backendname ] \n");
+ DEBUG(" [ -D ] [ -G ]\n");
+ DEBUG(" [ -S serialnum ] [ -B backendname ] \n");
DEBUG(" [ -V extra_vid ] [ -P extra_pid ] [ -T extra_type ] \n");
- DEBUG(" [ [ backend_specific_args ] | [ - | infile ] ]\n");
+ DEBUG(" [ backend_specific_args ] \n");
+ DEBUG(" [ -d copies ] [ - | infile ] \n");
for (i = 0; ; i++) {
backend = backends[i];
if (!backend)
@@ -506,14 +635,18 @@ static void print_help(char *argv0, struct dyesub_backend *backend)
DEBUG("Standalone %s backend version %s\n",
backend->name, backend->version);
DEBUG("\t%s\n", backend->uri_prefix);
- DEBUG("\t[ -D ] [ -S serialnum ] \n");
+ DEBUG("\t[ -D ] [ -G ] [ -S serialnum ] \n");
DEBUG("\t[ -V extra_vid ] [ -P extra_pid ] [ -T extra_type ] \n");
- DEBUG("\t\t[ infile | - ]\n");
-
if (backend->cmdline_usage)
backend->cmdline_usage();
+ DEBUG("\t[ -d copies ] [ infile | - ]\n");
+ }
+
+ i = libusb_init(&ctx);
+ if (i) {
+ ERROR("Failed to initialize libusb (%d)\n", i);
+ exit(4); /* CUPS_BACKEND_STOP */
}
- libusb_init(&ctx);
find_and_enumerate(ctx, &list, backend, NULL, P_ANY, 1);
libusb_free_device_list(list, 1);
libusb_exit(ctx);
@@ -584,7 +717,7 @@ int main (int argc, char **argv)
/* Reset arg parsing */
optind = 1;
opterr = 0;
- while ((i = getopt(argc, argv, "B:DGhP:S:T:V:")) >= 0) {
+ while ((i = getopt(argc, argv, "B:dDGhP:S:T:V:")) >= 0) {
switch(i) {
case 'B':
backend = find_backend(optarg);
@@ -592,6 +725,9 @@ int main (int argc, char **argv)
fprintf(stderr, "ERROR: Unknown backend '%s'\n", optarg);
}
break;
+ case 'd':
+ copies = atoi(optarg);
+ break;
case 'D':
dyesub_debug++;
break;
@@ -627,13 +763,14 @@ int main (int argc, char **argv)
}
}
+#ifndef LIBUSB_PRE_1_0_10
if (dyesub_debug) {
const struct libusb_version *ver;
ver = libusb_get_version();
DEBUG(" ** running with libusb %d.%d.%d%s (%d)\n",
ver->major, ver->minor, ver->micro, (ver->rc? ver->rc : ""), ver->nano );
-
}
+#endif
/* Make sure a filename was specified */
if (!backend_cmd && (optind == argc || !argv[optind])) {
@@ -746,10 +883,17 @@ int main (int argc, char **argv)
}
/* Libusb setup */
- libusb_init(&ctx);
+ ret = libusb_init(&ctx);
+ if (ret) {
+ ERROR("Failed to initialize libusb (%d)\n", ret);
+ ret = 4;
+ goto done;
+ }
+
/* Enumerate devices */
found = find_and_enumerate(ctx, &list, backend, use_serno, printer_type, 0);
+#if 1
if (found == -1) {
ERROR("Printer open failure (No suitable printers found!)\n");
ret = 4; /* CUPS_BACKEND_STOP */
@@ -761,7 +905,7 @@ int main (int argc, char **argv)
ERROR("Printer open failure (Need to be root?) (%d)\n", ret);
goto done;
}
-
+
claimed = libusb_kernel_driver_active(dev, iface);
if (claimed) {
ret = libusb_detach_kernel_driver(dev, iface);
@@ -791,16 +935,16 @@ int main (int argc, char **argv)
endp_down = config->interface[0].altsetting[0].endpoint[i].bEndpointAddress;
}
}
-
+#endif
/* Attach backend to device */
backend->attach(backend_ctx, dev, endp_up, endp_down, jobid);
-
+
if (backend_cmd && !uri) {
if (backend->cmdline_arg(backend_ctx, argc, argv))
goto done_claimed;
if (!fname)
goto done_claimed;
- }
+ }
/* Time for the main processing loop */
INFO("Printing started (%d copies)\n", copies);
diff --git a/src/cups/blacklist b/src/cups/blacklist
index 02e3ae7..204a8bc 100644
--- a/src/cups/blacklist
+++ b/src/cups/blacklist
@@ -34,7 +34,7 @@
0x04a9 0x3128 blacklist
# Canon SELPHY CP520
-# ??? UNKNOWN
+0x04a9 0x3172 blacklist
# Canon SELPHY CP530
0x04a9 0x31b1 blacklist
@@ -75,15 +75,9 @@
# Canon SELPHY CP810
0x04a9 0x3256 blacklist
-# Canon SELPHY CP820
-# ??? UNKNOWN
-
# Canon SELPHY CP900
0x04a9 0x3255 blacklist
-# Canon SELPHY CP910
-# ??? UNKNOWN
-
# Canon SELPHY ES1
0x04a9 0x3141 blacklist
@@ -126,6 +120,9 @@
# Mitsubishi CP-D70/CP-D707
0x06d3 0x3b30 blacklist
+# Mitsubishi CP-K60DW-S
+0x06d3 0x3b31 blacklist
+
# DNP DS40 + Citizen CX
0x1343 0x0003 blacklist
diff --git a/src/cups/mitsu70x_print.c b/src/cups/mitsu70x_print.c
index bdfc427..72f5f2e 100644
--- a/src/cups/mitsu70x_print.c
+++ b/src/cups/mitsu70x_print.c
@@ -39,6 +39,7 @@
#define USB_VID_MITSU 0x06D3
#define USB_PID_MITSU_D70X 0x3B30
+#define USB_PID_MITSU_K60 0x3B31
/* Private data stucture */
struct mitsu70x_ctx {
@@ -75,17 +76,12 @@ static void mitsu70x_attach(void *vctx, struct libusb_device_handle *dev,
uint8_t endp_up, uint8_t endp_down, uint8_t jobid)
{
struct mitsu70x_ctx *ctx = vctx;
- struct libusb_device *device;
- struct libusb_device_descriptor desc;
UNUSED(jobid);
ctx->dev = dev;
ctx->endp_up = endp_up;
ctx->endp_down = endp_down;
-
- device = libusb_get_device(dev);
- libusb_get_device_descriptor(device, &desc);
}
@@ -158,13 +154,14 @@ static int mitsu70x_read_parse(void *vctx, int data_fd) {
remain = be16_to_cpu(mhdr->rows) * be16_to_cpu(mhdr->cols) * 2;
remain = (remain + 511) / 512 * 512; /* Round to nearest 512 bytes. */
remain *= 3; /* One for each plane */
+
if (mhdr->laminate) {
i = be16_to_cpu(mhdr->lamrows) * be16_to_cpu(mhdr->lamcols) * 2;
i = (i + 511) / 512 * 512; /* Round to nearest 512 bytes. */
remain += i;
}
- ctx->databuf = malloc(remain + sizeof(hdr));
+ ctx->databuf = malloc(sizeof(hdr) + remain);
if (!ctx->databuf) {
ERROR("Memory allocation failure!\n");
return 2;
@@ -175,9 +172,12 @@ static int mitsu70x_read_parse(void *vctx, int data_fd) {
/* Read in the spool data */
while(remain) {
- i = read(data_fd, ctx->databuf + ctx->datalen - remain, remain);
+ i = read(data_fd, ctx->databuf + ctx->datalen, remain);
+ if (i == 0)
+ return 1;
if (i < 0)
return i;
+ ctx->datalen += i;
remain -= i;
}
@@ -241,6 +241,15 @@ skip_query:
return 4;
}
+ if (dyesub_debug) {
+ unsigned int i;
+ DEBUG("Printer Status Dump: ");
+ for (i = 0 ; i < 26 ; i++) {
+ DEBUG2("%02x ", rdbuf[i]);
+ }
+ DEBUG2("\n");
+ }
+
if (memcmp(rdbuf, rdbuf2, READBACK_LEN)) {
memcpy(rdbuf2, rdbuf, READBACK_LEN);
} else if (state == last_state) {
@@ -313,6 +322,10 @@ skip_query:
struct mitsu70x_status_deck {
uint8_t unk[64];
+ // unk[0] 0x80 for NOT PRESENT, 0x00 for present.
+ // unk[7-8] 0x01ff or 0x0200? Changes; maybe status?
+ // unk[22-23] prints remaining, 16-bit BE
+
};
struct mitsu70x_status_resp {
@@ -366,8 +379,14 @@ static int mitsu70x_get_status(struct mitsu70x_ctx *ctx)
}
DEBUG2("\n");
}
- INFO("Prints remaining: Lower: %d Upper: %d\n",
- resp.lower.unk[23], resp.upper.unk[23]);
+ if (resp.upper.unk[0] & 0x80) { /* Not present */
+ INFO("Prints remaining: %d\n",
+ (resp.lower.unk[22] << 8) | resp.lower.unk[23]);
+ } else {
+ INFO("Prints remaining: Lower: %d Upper: %d\n",
+ (resp.lower.unk[22] << 8) | resp.lower.unk[23],
+ (resp.upper.unk[22] << 8) | resp.upper.unk[23]);
+ }
return 0;
}
@@ -406,8 +425,8 @@ static int mitsu70x_cmdline_arg(void *vctx, int argc, char **argv)
/* Exported */
struct dyesub_backend mitsu70x_backend = {
- .name = "Mitsubishi CP-D70/D707",
- .version = "0.12",
+ .name = "Mitsubishi CP-D70/D707/K60",
+ .version = "0.16",
.uri_prefix = "mitsu70x",
.cmdline_usage = mitsu70x_cmdline,
.cmdline_arg = mitsu70x_cmdline_arg,
@@ -417,7 +436,8 @@ struct dyesub_backend mitsu70x_backend = {
.read_parse = mitsu70x_read_parse,
.main_loop = mitsu70x_main_loop,
.devices = {
- { USB_VID_MITSU, USB_PID_MITSU_D70X, P_MITSU_D70X, "Mitsubishi"},
+ { USB_VID_MITSU, USB_PID_MITSU_D70X, P_MITSU_D70X, ""},
+ { USB_VID_MITSU, USB_PID_MITSU_K60, P_MITSU_D70X, ""},
{ 0, 0, 0, ""}
}
};
@@ -440,16 +460,19 @@ struct dyesub_backend mitsu70x_backend = {
1b 5a 54 01 00 00 00 00 00 00 00 00 00 00 00 00
XX XX YY YY QQ QQ ZZ ZZ SS 00 00 00 00 00 00 00
UU 00 00 00 00 00 00 00 00 TT 00 00 00 00 00 00
+ RR 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+
(padded by NULLs to a 512-byte boundary)
XX XX == columns
YY YY == rows
QQ QQ == lamination columns (equal to XX XX)
ZZ ZZ == lamination rows (YY YY + 12)
- SS == SuperFine mode (00 == off, 03 == on
- Lamination always turns this on!
+ SS == Print mode: 00 = Fine, 03 = SuperFine, 04 = UltraFine
+ (Matte requires Superfine or Ultrafine)
UU == 00 == Auto, 01 == Lower Deck, 02 == Upper Deck
TT == 00 with no lamination, 02 with.
+ RR == 00 (normal), 01 == (Double-cut 4x6), 05 == (double-cut 2x6)
[[ K60 ]] Header 2: (Header)
@@ -464,10 +487,11 @@ struct dyesub_backend mitsu70x_backend = {
YY YY == rows
QQ QQ == lamination columns (equal to XX XX)
ZZ ZZ == lamination rows (usually YY YY + 12)
- SS == UltraFine mode (00 == off, 04 == on.. forces 8x6 print?)
+ SS == Print mode: 00 = Fine, 04 = UltraFine
+ (Matte requires Ultrafine)
UU == 01 (Lower Deck)
TT == 00 with no lamination, 02 with.
- RR == 0x05 for double-cut 2x6, 0x00 for double-cut 4x6, otherwise 0x01
+ RR == 00 (normal), 01 == (Double-cut 4x6), 05 == (double-cut 2x6)
Data planes:
16-bit data, rounded up to 512-byte block (XX * YY * 2 bytes)
@@ -479,52 +503,83 @@ struct dyesub_backend mitsu70x_backend = {
********************************************************************
- Command format: (D70/D707)
+ Command format: (D707)
-> 1b 56 32 30
- <- [256 byte payload]
-
- e4 56 32 30 00 00 00 00 00 00 00 00 00 00 00 00 .V20............
- 00 00 00 00 00 00 00 00 00 00 00 80 00 00 00 00 ................
- 44 80 00 00 5f 00 00 3d 43 00 50 00 44 00 37 00 D..._..=C.P.D.7.
- 30 00 44 00 30 00 30 00 31 00 31 00 31 00 37 00 0.D.0.0.1.1.1.7.
- 33 31 36 54 31 33 21 a3 33 31 35 42 31 32 f5 e5 316T13!.315B12..
- 33 31 39 42 31 31 a3 fb 33 31 38 45 31 32 50 0d 319B11..318E12P.
- 33 31 37 41 32 32 a3 82 44 55 4d 4d 59 40 00 00 317A22..DUMMY@..
- 44 55 4d 4d 59 40 00 00 00 00 00 00 00 00 00 00 DUMMY@..........
-
- LOWER DECK
-
- 00 00 00 00 00 00 02 04 3f 00 00 04 96 00 00 00 ........?.......
- ff 0f 01 00 00 c8 NN NN 00 00 00 00 05 28 75 80 .......R.....(u.
- 80 00 80 00 80 00 80 00 80 00 80 00 80 00 80 00 ................
- 80 00 80 00 80 00 80 00 80 00 80 00 80 00 80 00 ................
-
- UPPER DECK
-
- 00 00 00 00 00 00 01 ee 3d 00 00 06 39 00 00 00 ........=...9...
- ff 02 00 00 01 90 NN NN 00 00 00 00 06 67 78 00 .............gx.
- 80 00 80 00 80 00 80 00 80 00 80 00 80 00 80 00 ................
- 80 00 80 00 80 00 80 00 80 00 80 00 80 00 80 00 ................
+ <- [256 byte payload]
- NN NN == Number of prints remaining on that deck.
- (None of the other fields are decoded yet)
+ CP-D707DW:
+
+ e4 56 32 30 00 00 00 00 00 00 00 00 00 00 00 00 .V20............
+ 00 00 00 00 00 00 00 00 00 00 00 80 00 00 00 00 ................
+ 44 80 00 00 5f 00 00 3d 43 00 50 00 44 00 37 00 D..._..=C.P.D.7.
+ 30 00 44 00 30 00 30 00 31 00 31 00 31 00 37 00 0.D.0.0.1.1.1.7.
+ 33 31 36 54 31 33 21 a3 33 31 35 42 31 32 f5 e5 316T13!.315B12..
+ 33 31 39 42 31 31 a3 fb 33 31 38 45 31 32 50 0d 319B11..318E12P.
+ 33 31 37 41 32 32 a3 82 44 55 4d 4d 59 40 00 00 317A22..DUMMY@..
+ 44 55 4d 4d 59 40 00 00 00 00 00 00 00 00 00 00 DUMMY@..........
+
+ LOWER DECK
+
+ 00 00 00 00 00 00 02 04 3f 00 00 04 96 00 00 00
+ ff 0f 01 00 00 c8 NN NN 00 00 00 00 05 28 75 80 NN NN: prints remaining
+ 80 00 80 00 80 00 80 00 80 00 80 00 80 00 80 00
+ 80 00 80 00 80 00 80 00 80 00 80 00 80 00 80 00
+
+ UPPER DECK
+
+ 00 00 00 00 00 00 01 ee 3d 00 00 06 39 00 00 00
+ ff 02 00 00 01 90 NN NN 00 00 00 00 06 67 78 00 NN NN: prints remaining
+ 80 00 80 00 80 00 80 00 80 00 80 00 80 00 80 00
+ 80 00 80 00 80 00 80 00 80 00 80 00 80 00 80 00
+
+ CP-K60DW-S:
+
+ e4 56 32 30 0f 00 00 00 00 00 00 00 00 00 00 00
+ 00 00 00 00 00 00 00 00 00 00 0a 80 00 00 00 00
+ 02 00 00 00 5e 00 04 87 43 00 50 00 4b 00 36 00
+ 30 00 44 00 30 00 32 00 33 00 32 00 30 00 36 00
+ 33 31 36 4b 33 31 d6 7a 33 31 35 41 33 31 ae 37
+ 33 31 39 41 37 31 6a 36 33 31 38 44 33 31 1e 4a
+ 33 31 37 42 32 31 f4 19 44 55 4d 4d 59 40 00 00
+ 44 55 4d 4d 59 40 00 00 00 00 00 00 00 00 00 00
+
+ LOWER DECK (K60)
+
+ 00 00 00 00 00 00 02 09 3f 00 00 00 05 00 00 01
+ 61 8f 00 00 01 40 NN NN 00 00 00 00 00 16 81 80 NN NN: prints remaining
+ 80 00 80 00 80 00 80 00 80 00 80 00 80 00 80 00
+ 80 00 80 00 80 00 80 00 80 00 80 00 80 00 80 00
+
+ UPPER DECK (K60 -- No upper deck present)
+
+ 80 00 00 00 00 00 00 ff ff 00 00 00 00 00 00 00
+ ff ff ff ff ff ff ff ff ff ff 00 00 00 00 80 00
+ 80 00 80 00 80 00 80 00 80 00 80 00 80 00 80 00
+ 80 00 80 00 80 00 80 00 80 00 80 00 80 00 80 00
-> 1b 56 31 30 00 00
<- [26 byte payload]
- e4 56 31 30 00 00 00 XX YY ZZ 00 00 00 00 00 00
- 00 00 00 00 00 00 00 00 00 00
-
- XX/YY/ZZ are unkown. Observed values:
+ CP-D707DW:
+
+ e4 56 31 30 00 00 00 XX YY ZZ 00 00 00 00 00 00
+ 00 00 00 00 00 00 00 00 00 00
+
+ XX/YY/ZZ are unkown. Observed values:
+
+ 00 00 00
+ 40 80 a0
+ 80 80 a0
+
+ CP-K60DW-S: (only one readback observed so far)
- 40 80 a0
- 00 00 00
- 80 80 a0
+ e4 56 31 30 00 00 00 00 00 00 00 00 0f 00 00 00
+ 00 00 00 00 80 00 00 00 00 00
** ** ** ** ** **
- The windows drivers seem to send the id and status queries before
+ The windows drivers seem to send the id and status queries before
and in between each of the chunks sent to the printer. There doesn't
appear to be any particular intelligence in the protocol, but it didn't
work when the raw dump was submitted as-is.
diff --git a/src/cups/selphy_print.c b/src/cups/selphy_print.c
index a15c572..7247e51 100644
--- a/src/cups/selphy_print.c
+++ b/src/cups/selphy_print.c
@@ -48,7 +48,7 @@
#define USB_PID_CANON_CP400 0x30F6
#define USB_PID_CANON_CP500 0x30F5
#define USB_PID_CANON_CP510 0x3128
-#define USB_PID_CANON_CP520 520 // XXX 316f? 3172? (related to cp740/cp750)
+#define USB_PID_CANON_CP520 0x3172
#define USB_PID_CANON_CP530 0x31b1
#define USB_PID_CANON_CP600 0x310B
#define USB_PID_CANON_CP710 0x3127
@@ -62,9 +62,7 @@
#define USB_PID_CANON_CP790 0x31E7
#define USB_PID_CANON_CP800 0x3214
#define USB_PID_CANON_CP810 0x3256
-#define USB_PID_CANON_CP820 820 // XXX
#define USB_PID_CANON_CP900 0x3255
-#define USB_PID_CANON_CP910 910 // XXX
#define USB_PID_CANON_ES1 0x3141
#define USB_PID_CANON_ES2 0x3185
#define USB_PID_CANON_ES20 0x3186
@@ -926,7 +924,7 @@ top:
struct dyesub_backend canonselphy_backend = {
.name = "Canon SELPHY CP/ES",
- .version = "0.81",
+ .version = "0.82.2G",
.uri_prefix = "canonselphy",
.init = canonselphy_init,
.attach = canonselphy_attach,
@@ -935,38 +933,36 @@ struct dyesub_backend canonselphy_backend = {
.read_parse = canonselphy_read_parse,
.main_loop = canonselphy_main_loop,
.devices = {
- { USB_VID_CANON, USB_PID_CANON_CP10, P_CP10, "Canon"},
- { USB_VID_CANON, USB_PID_CANON_CP100, P_CP_XXX, "Canon"},
- { USB_VID_CANON, USB_PID_CANON_CP200, P_CP_XXX, "Canon"},
- { USB_VID_CANON, USB_PID_CANON_CP220, P_CP_XXX, "Canon"},
- { USB_VID_CANON, USB_PID_CANON_CP300, P_CP_XXX, "Canon"},
- { USB_VID_CANON, USB_PID_CANON_CP330, P_CP_XXX, "Canon"},
- { USB_VID_CANON, USB_PID_CANON_CP400, P_CP_XXX, "Canon"},
- { USB_VID_CANON, USB_PID_CANON_CP500, P_CP_XXX, "Canon"},
- { USB_VID_CANON, USB_PID_CANON_CP510, P_CP_XXX, "Canon"},
- { USB_VID_CANON, USB_PID_CANON_CP520, P_CP_XXX, "Canon"},
- { USB_VID_CANON, USB_PID_CANON_CP530, P_CP_XXX, "Canon"},
- { USB_VID_CANON, USB_PID_CANON_CP600, P_CP_XXX, "Canon"},
- { USB_VID_CANON, USB_PID_CANON_CP710, P_CP_XXX, "Canon"},
- { USB_VID_CANON, USB_PID_CANON_CP720, P_CP_XXX, "Canon"},
- { USB_VID_CANON, USB_PID_CANON_CP730, P_CP_XXX, "Canon"},
- { USB_VID_CANON, USB_PID_CANON_CP740, P_CP_XXX, "Canon"},
- { USB_VID_CANON, USB_PID_CANON_CP750, P_CP_XXX, "Canon"},
- { USB_VID_CANON, USB_PID_CANON_CP760, P_CP_XXX, "Canon"},
- { USB_VID_CANON, USB_PID_CANON_CP770, P_CP_XXX, "Canon"},
- { USB_VID_CANON, USB_PID_CANON_CP780, P_CP_XXX, "Canon"},
- { USB_VID_CANON, USB_PID_CANON_CP790, P_ES40_CP790, "Canon"},
- { USB_VID_CANON, USB_PID_CANON_CP800, P_CP_XXX, "Canon"},
- { USB_VID_CANON, USB_PID_CANON_CP810, P_CP_XXX, "Canon"},
- { USB_VID_CANON, USB_PID_CANON_CP820, P_CP_XXX, "Canon"},
- { USB_VID_CANON, USB_PID_CANON_CP900, P_CP_XXX, "Canon"},
- { USB_VID_CANON, USB_PID_CANON_CP910, P_CP_XXX, "Canon"},
- { USB_VID_CANON, USB_PID_CANON_ES1, P_ES1, "Canon"},
- { USB_VID_CANON, USB_PID_CANON_ES2, P_ES2_20, "Canon"},
- { USB_VID_CANON, USB_PID_CANON_ES20, P_ES2_20, "Canon"},
- { USB_VID_CANON, USB_PID_CANON_ES3, P_ES3_30, "Canon"},
- { USB_VID_CANON, USB_PID_CANON_ES30, P_ES3_30, "Canon"},
- { USB_VID_CANON, USB_PID_CANON_ES40, P_ES40_CP790, "Canon"},
+ { USB_VID_CANON, USB_PID_CANON_CP10, P_CP10, ""},
+ { USB_VID_CANON, USB_PID_CANON_CP100, P_CP_XXX, ""},
+ { USB_VID_CANON, USB_PID_CANON_CP200, P_CP_XXX, ""},
+ { USB_VID_CANON, USB_PID_CANON_CP220, P_CP_XXX, ""},
+ { USB_VID_CANON, USB_PID_CANON_CP300, P_CP_XXX, ""},
+ { USB_VID_CANON, USB_PID_CANON_CP330, P_CP_XXX, ""},
+ { USB_VID_CANON, USB_PID_CANON_CP400, P_CP_XXX, ""},
+ { USB_VID_CANON, USB_PID_CANON_CP500, P_CP_XXX, ""},
+ { USB_VID_CANON, USB_PID_CANON_CP510, P_CP_XXX, ""},
+ { USB_VID_CANON, USB_PID_CANON_CP520, P_CP_XXX, ""},
+ { USB_VID_CANON, USB_PID_CANON_CP530, P_CP_XXX, ""},
+ { USB_VID_CANON, USB_PID_CANON_CP600, P_CP_XXX, ""},
+ { USB_VID_CANON, USB_PID_CANON_CP710, P_CP_XXX, ""},
+ { USB_VID_CANON, USB_PID_CANON_CP720, P_CP_XXX, ""},
+ { USB_VID_CANON, USB_PID_CANON_CP730, P_CP_XXX, ""},
+ { USB_VID_CANON, USB_PID_CANON_CP740, P_CP_XXX, ""},
+ { USB_VID_CANON, USB_PID_CANON_CP750, P_CP_XXX, ""},
+ { USB_VID_CANON, USB_PID_CANON_CP760, P_CP_XXX, ""},
+ { USB_VID_CANON, USB_PID_CANON_CP770, P_CP_XXX, ""},
+ { USB_VID_CANON, USB_PID_CANON_CP780, P_CP_XXX, ""},
+ { USB_VID_CANON, USB_PID_CANON_CP790, P_ES40_CP790, ""},
+ { USB_VID_CANON, USB_PID_CANON_CP800, P_CP_XXX, ""},
+ { USB_VID_CANON, USB_PID_CANON_CP810, P_CP_XXX, ""},
+ { USB_VID_CANON, USB_PID_CANON_CP900, P_CP_XXX, ""},
+ { USB_VID_CANON, USB_PID_CANON_ES1, P_ES1, ""},
+ { USB_VID_CANON, USB_PID_CANON_ES2, P_ES2_20, ""},
+ { USB_VID_CANON, USB_PID_CANON_ES20, P_ES2_20, ""},
+ { USB_VID_CANON, USB_PID_CANON_ES3, P_ES3_30, ""},
+ { USB_VID_CANON, USB_PID_CANON_ES30, P_ES3_30, ""},
+ { USB_VID_CANON, USB_PID_CANON_ES40, P_ES40_CP790, ""},
{ 0, 0, 0, ""}
}
};
@@ -1281,5 +1277,36 @@ struct dyesub_backend canonselphy_backend = {
0x41 if the 'Wide' paper tray is loaded with a 'P' ribbon. A '0' is used
to signify nothing being loaded.
+ ***************************************************************************
+ Selphy CP820/CP910:
+
+ Radically different spool file format! 300dpi, same print sizes, but also
+ adding a 50x50mm sticker and 22x17.3mm ministickers, though I think the
+ driver treats all of those as 'C' sizes for printing purposes.
+
+ 32-byte header:
+
+ 0f 00 00 40 00 00 00 00 00 00 00 00 00 00 01 00
+ 01 00 ?? 00 00 00 00 00 XX 04 00 00 WW ZZ 00 00
+
+ ?? == 50 (P)
+ == 4c (L)
+ == 43 (C)
+
+ XX == e0 (P)
+ 80 (L)
+ 40 (C)
+
+ WW == 50 (P)
+ c0 (L)
+ 9c (C)
+
+ ZZ == 07 (P)
+ 05 (L)
+ 02 (C)
+
+ P == 7008800 == 2336256 * 3 + 32 (4.884% larger than CP)
+ L == 5087264 == 1695744 * 3 + 32 (5.878% larger than CP)
+ C == 2180384 == 726784 * 3 + 32 (3.991% larger than CP)
*/