Discussion:
[PATCH 2/3] Add ICC profile embedding for PNG output.
Add Reply
Aaron Muir Hamilton
2017-04-17 12:07:39 UTC
Reply
Permalink
Raw Message
---
frontend/scanimage.c | 21 ++++++++++++++++++---
1 file changed, 18 insertions(+), 3 deletions(-)

diff --git a/frontend/scanimage.c b/frontend/scanimage.c
index 77c22883..0f71422c 100644
--- a/frontend/scanimage.c
+++ b/frontend/scanimage.c
@@ -56,6 +56,7 @@
#include "../include/sane/sanei.h"
#include "../include/sane/saneopts.h"

+#include "sicc.h"
#include "stiff.h"

#include "../include/md5.h"
@@ -1165,9 +1166,11 @@ write_pnm_header (SANE_Frame format, int width, int height, int depth, FILE *ofp

#ifdef HAVE_LIBPNG
static void
-write_png_header (SANE_Frame format, int width, int height, int depth, FILE *ofp, png_structp* png_ptr, png_infop* info_ptr)
+write_png_header (SANE_Frame format, int width, int height, int depth, const char * icc_profile, FILE *ofp, png_structp* png_ptr, png_infop* info_ptr)
{
int color_type;
+ size_t icc_size = 0;
+ void *icc_buffer;

*png_ptr = png_create_write_struct
(PNG_LIBPNG_VER_STRING, NULL, NULL, NULL);
@@ -1200,6 +1203,16 @@ write_png_header (SANE_Frame format, int width, int height, int depth, FILE *ofp
depth, color_type, PNG_INTERLACE_NONE,
PNG_COMPRESSION_TYPE_BASE, PNG_FILTER_TYPE_BASE);

+ if (icc_profile)
+ {
+ icc_buffer = sanei_load_icc_profile(icc_profile, &icc_size);
+ if (icc_size > 0)
+ {
+ png_set_iCCP(*png_ptr, *info_ptr, basename(icc_profile), PNG_COMPRESSION_TYPE_BASE, icc_buffer, icc_size);
+ free(icc_buffer);
+ }
+ }
+
png_write_info(*png_ptr, *info_ptr);
}
#endif
@@ -1379,7 +1392,8 @@ scan_it (FILE *ofp)
#ifdef HAVE_LIBPNG
case OUTPUT_PNG:
write_png_header (parm.format, parm.pixels_per_line,
- parm.lines, parm.depth, ofp, &png_ptr, &info_ptr);
+ parm.lines, parm.depth, icc_profile,
+ ofp, &png_ptr, &info_ptr);
break;
#endif
#ifdef HAVE_LIBJPEG
@@ -1635,7 +1649,8 @@ scan_it (FILE *ofp)
#ifdef HAVE_LIBPNG
case OUTPUT_PNG:
write_png_header (parm.format, parm.pixels_per_line,
- image.height, parm.depth, ofp, &png_ptr, &info_ptr);
+ image.height, parm.depth, icc_profile,
+ ofp, &png_ptr, &info_ptr);
break;
#endif
#ifdef HAVE_LIBJPEG
--
2.12.2
--
sane-devel mailing list: sane-***@lists.alioth.debian.org
http://lists.alioth.debian.org/cgi-bin/mailman/listinfo/sane-devel
Unsubscribe: Send mail with subject "unsubscribe your_password"
to sane-devel-***@lists.alioth.debian.org
Aaron Muir Hamilton
2017-04-17 12:07:40 UTC
Reply
Permalink
Raw Message
If the ICC profile added does not match the colour format of the
image, libpng will abort. This can leave the scanner motors in an
incorrect state and possibly cause permanent damage.
---
frontend/scanimage.c | 22 +++++++++++++++++++++-
1 file changed, 21 insertions(+), 1 deletion(-)

diff --git a/frontend/scanimage.c b/frontend/scanimage.c
index 0f71422c..74546763 100644
--- a/frontend/scanimage.c
+++ b/frontend/scanimage.c
@@ -1208,7 +1208,27 @@ write_png_header (SANE_Frame format, int width, int height, int depth, const cha
icc_buffer = sanei_load_icc_profile(icc_profile, &icc_size);
if (icc_size > 0)
{
- png_set_iCCP(*png_ptr, *info_ptr, basename(icc_profile), PNG_COMPRESSION_TYPE_BASE, icc_buffer, icc_size);
+ /* libpng will abort if the profile and image colour spaces do not match*/
+ /* The data colour space field is at bytes 16 to 20 in an ICC profile */
+ /* see: ICC.1:2010 § 7.2.6 */
+ int is_gray_profile = strncmp(icc_buffer + 16, "GRAY", 4) == 0;
+ int is_rgb_profile = strncmp(icc_buffer + 16, "RGB ", 4) == 0;
+ if ((is_gray_profile && color_type == PNG_COLOR_TYPE_GRAY) ||
+ (is_rgb_profile && color_type == PNG_COLOR_TYPE_RGB))
+ {
+ png_set_iCCP(*png_ptr, *info_ptr, basename(icc_profile), PNG_COMPRESSION_TYPE_BASE, icc_buffer, icc_size);
+ }
+ else
+ {
+ if (is_gray_profile)
+ {
+ fprintf(stderr, "Ignoring 'GRAY' space ICC profile because the image is RGB.\n");
+ }
+ if (is_rgb_profile)
+ {
+ fprintf(stderr, "Ignoring 'RGB ' space ICC profile because the image is Grayscale.\n");
+ }
+ }
free(icc_buffer);
}
}
--
2.12.2
--
sane-devel mailing list: sane-***@lists.alioth.debian.org
http://lists.alioth.debian.org/cgi-bin/mailman/listinfo/sane-devel
Unsubscribe: Send mail with subject "unsubscribe your_password"
to sane-devel-***@lists.alioth.debia
Olaf Meeuwissen
2017-04-30 11:18:26 UTC
Reply
Permalink
Raw Message
Hi Aaron,

I'm working on your ICC profile patches but this one made me wonder what
happens with monochrome scans, i.e. grayscale with a bit depth of one.
If that works fine, I'll push your patches with two fixes after merging
against master.
Post by Aaron Muir Hamilton
If the ICC profile added does not match the colour format of the
image, libpng will abort. This can leave the scanner motors in an
incorrect state and possibly cause permanent damage.
---
frontend/scanimage.c | 22 +++++++++++++++++++++-
1 file changed, 21 insertions(+), 1 deletion(-)
diff --git a/frontend/scanimage.c b/frontend/scanimage.c
index 0f71422c..74546763 100644
--- a/frontend/scanimage.c
+++ b/frontend/scanimage.c
@@ -1208,7 +1208,27 @@ write_png_header (SANE_Frame format, int width, int height, int depth, const cha
icc_buffer = sanei_load_icc_profile(icc_profile, &icc_size);
if (icc_size > 0)
{
- png_set_iCCP(*png_ptr, *info_ptr, basename(icc_profile), PNG_COMPRESSION_TYPE_BASE, icc_buffer, icc_size);
+ /* libpng will abort if the profile and image colour spaces do not match*/
+ /* The data colour space field is at bytes 16 to 20 in an ICC profile */
+ /* see: ICC.1:2010 § 7.2.6 */
+ int is_gray_profile = strncmp(icc_buffer + 16, "GRAY", 4) == 0;
+ int is_rgb_profile = strncmp(icc_buffer + 16, "RGB ", 4) == 0;
+ if ((is_gray_profile && color_type == PNG_COLOR_TYPE_GRAY) ||
+ (is_rgb_profile && color_type == PNG_COLOR_TYPE_RGB))
+ {
+ png_set_iCCP(*png_ptr, *info_ptr, basename(icc_profile), PNG_COMPRESSION_TYPE_BASE, icc_buffer, icc_size);
+ }
+ else
+ {
+ if (is_gray_profile)
+ {
+ fprintf(stderr, "Ignoring 'GRAY' space ICC profile because the image is RGB.\n");
+ }
+ if (is_rgb_profile)
+ {
+ fprintf(stderr, "Ignoring 'RGB ' space ICC profile because the image is Grayscale.\n");
+ }
+ }
free(icc_buffer);
}
}
--
2.12.2
--
Olaf Meeuwissen, LPIC-2 FSF Associate Member since 2004-01-27
GnuPG key: F84A2DD9/B3C0 2F47 EA19 64F4 9F13 F43E B8A4 A88A F84A 2DD9
Support Free Software https://my.fsf.org/donate
Join the Free Software Foundation https://my.fsf.org/join
--
sane-devel mailing list: sane-***@lists.alioth.debian.org
http://lists.alioth.debian.org/cgi-bin/mailman/listinfo/sane-devel
Unsubscribe: Send mail with subject "unsubscribe your_password"
to sane-devel-***@lists.alioth.debian.org
Aaron Muir Hamilton
2017-05-01 22:29:20 UTC
Reply
Permalink
Raw Message
Post by Olaf Meeuwissen
Hi Aaron,
I'm working on your ICC profile patches but this one made me wonder what
happens with monochrome scans, i.e. grayscale with a bit depth of one.
Unfortunately, 1-bit images are not supported by genesys, and I don't
think I have any other scanners set up to try this with.

Maybe somebody else could test it with another scanner.
I don't personally work with Grayscale profiles at all, but if you need
a profile to test with, there are downloads on this page:
https://www.idealliance.org/gracol/
Any one of these profiles should be fine to determine if 1-bit images
with Grayscale profiles work in libpng.


I would say that it's probably safe though, because libpng only
complains if the type is mismatched. 1-bit (as well as 2-, 4-, 8-, and
16-bit) are considered to be PNG_COLOR_TYPE_GRAY.

I think that since it works correctly with 8- and 16-bit modes
correctly, it should also work with the other libpng grayscale modes.
Post by Olaf Meeuwissen
If that works fine, I'll push your patches with two fixes after merging
against master.
Post by Aaron Muir Hamilton
If the ICC profile added does not match the colour format of the
image, libpng will abort. This can leave the scanner motors in an
incorrect state and possibly cause permanent damage.
---
frontend/scanimage.c | 22 +++++++++++++++++++++-
1 file changed, 21 insertions(+), 1 deletion(-)
diff --git a/frontend/scanimage.c b/frontend/scanimage.c
index 0f71422c..74546763 100644
--- a/frontend/scanimage.c
+++ b/frontend/scanimage.c
@@ -1208,7 +1208,27 @@ write_png_header (SANE_Frame format, int width, int height, int depth, const cha
icc_buffer = sanei_load_icc_profile(icc_profile, &icc_size);
if (icc_size > 0)
{
- png_set_iCCP(*png_ptr, *info_ptr, basename(icc_profile), PNG_COMPRESSION_TYPE_BASE, icc_buffer, icc_size);
+ /* libpng will abort if the profile and image colour spaces do not match*/
+ /* The data colour space field is at bytes 16 to 20 in an ICC profile */
+ /* see: ICC.1:2010 § 7.2.6 */
+ int is_gray_profile = strncmp(icc_buffer + 16, "GRAY", 4) == 0;
+ int is_rgb_profile = strncmp(icc_buffer + 16, "RGB ", 4) == 0;
+ if ((is_gray_profile && color_type == PNG_COLOR_TYPE_GRAY) ||
+ (is_rgb_profile && color_type == PNG_COLOR_TYPE_RGB))
+ {
+ png_set_iCCP(*png_ptr, *info_ptr, basename(icc_profile), PNG_COMPRESSION_TYPE_BASE, icc_buffer, icc_size);
+ }
+ else
+ {
+ if (is_gray_profile)
+ {
+ fprintf(stderr, "Ignoring 'GRAY' space ICC profile because the image is RGB.\n");
+ }
+ if (is_rgb_profile)
+ {
+ fprintf(stderr, "Ignoring 'RGB ' space ICC profile because the image is Grayscale.\n");
+ }
+ }
free(icc_buffer);
}
}
--
2.12.2
--
Olaf Meeuwissen, LPIC-2 FSF Associate Member since 2004-01-27
GnuPG key: F84A2DD9/B3C0 2F47 EA19 64F4 9F13 F43E B8A4 A88A F84A 2DD9
Support Free Software https://my.fsf.org/donate
Join the Free Software Foundation https://my.fsf.org/join
--
sane-devel mailing list: sane-***@lists.alioth.debian.org
http://lists.alioth.debian.org/cgi-bin/mailman/listinfo/sane-devel
Unsubscribe: Send mail with subject "unsubscribe your_password"
to sane-devel-
Aaron Muir Hamilton
2017-05-01 23:36:28 UTC
Reply
Permalink
Raw Message
I just tried it by hacking scanimage up a bit to threshhold and convert
the lines to monochrome right before writing the PNG, and change the PNG
header to always be 1-bit; libpng didn't complain about attaching a
grayscale profile to a 1-bit monochrome image.
--
sane-devel mailing list: sane-***@lists.alioth.debian.org
http://lists.alioth.debian.org/cgi-bin/mailman/listinfo/sane-devel
Unsubscribe: Send mail with subject "unsubscribe your_password"
to sane-devel-***@lists.alioth.debian.org
Olaf Meeuwissen
2017-05-04 09:18:26 UTC
Reply
Permalink
Raw Message
Hi Aaron
Post by Aaron Muir Hamilton
I just tried it by hacking scanimage up a bit to threshhold and convert
the lines to monochrome right before writing the PNG, and change the PNG
header to always be 1-bit; libpng didn't complain about attaching a
grayscale profile to a 1-bit monochrome image.
Ok so based on this and your comment in the previous mail in this thread
I'll just go ahead and merge against HEAD and push the changes to Alioth.

Hope this helps,
--
Olaf Meeuwissen, LPIC-2 FSF Associate Member since 2004-01-27
GnuPG key: F84A2DD9/B3C0 2F47 EA19 64F4 9F13 F43E B8A4 A88A F84A 2DD9
Support Free Software https://my.fsf.org/donate
Join the Free Software Foundation https://my.fsf.org/join
--
sane-devel mailing list: sane-***@lists.alioth.debian.org
http://lists.alioth.debian.org/cgi-bin/mailman/listinfo/sane-devel
Unsubscribe: Send mail with subject "unsubscribe your_password"
to sane-devel-***@lists.alioth.debian.org
thierry
2017-04-17 17:54:59 UTC
Reply
Permalink
Raw Message
Hello,

This little patch add support to Canon MF230 Series scanner.
Tested OK (network only) on my MF232w :
[bjnp] get_scanner_id: Scanner identity string =
MFG:CANON;CMD:MFNP1,MultiPASS 2.1;MDL:Canon MF230
Series;CLS:IMG;DES:Canon MF230 Series; - length = 88
[bjnp] get_scanner_id: Scanner model = Canon MF230 Series

Please commit.
Best regards
Peter Talbott
2017-04-19 19:47:16 UTC
Reply
Permalink
Raw Message
Hello,

I also have a Canon ImageClass MF232.

I added that patch into the pixma_imageclass.c file, recompiled the sane backeneds and it seems to work perfectly.

Thank You!


On 04/17/2017 01:54 PM, thierry wrote:

Hello,

This little patch add support to Canon MF230 Series scanner.
Tested OK (network only) on my MF232w :
[bjnp] get_scanner_id: Scanner identity string =
MFG:CANON;CMD:MFNP1,MultiPASS 2.1;MDL:Canon MF230
Series;CLS:IMG;DES:Canon MF230 Series; - length = 88
[bjnp] get_scanner_id: Scanner model = Canon MF230 Series

Please commit.
Best regards
Rolf Bensch
2017-04-26 09:51:02 UTC
Reply
Permalink
Raw Message
Hello,

I just committed the patch to the git repository (pixma backend version
= 0.17.36) and updated the doc files. I also added the new scanners
i-SENSYS MF240 Series

Many thanks for your help.

Cheers,
Rolf
Hello,
I also have a Canon ImageClass MF232.
I added that patch into the pixma_imageclass.c file, recompiled the
sane backeneds and it seems to work perfectly.
Thank You!
Post by thierry
Hello,
This little patch add support to Canon MF230 Series scanner.
[bjnp] get_scanner_id: Scanner identity string =
MFG:CANON;CMD:MFNP1,MultiPASS 2.1;MDL:Canon MF230
Series;CLS:IMG;DES:Canon MF230 Series; - length = 88
[bjnp] get_scanner_id: Scanner model = Canon MF230 Series
Please commit.
Best regards
Rolf Bensch
2017-05-19 08:36:16 UTC
Reply
Permalink
Raw Message
Hello,

I just got a report from a MF240 Series scanner that only 300dpi is
possible (allowed) scanning from the document feeder. Please test this
and report your results.

Many thanks for your help in advance.

Cheers,
Rolf
Post by thierry
Hello,
I just committed the patch to the git repository (pixma backend
version >= 0.17.36) and updated the doc files. I also added the new
scanners i-SENSYS MF240 Series
Many thanks for your help.
Cheers,
Rolf
Post by thierry
Hello,
I also have a Canon ImageClass MF232.
I added that patch into the pixma_imageclass.c file, recompiled the
sane backeneds and it seems to work perfectly.
Thank You!
Post by thierry
Hello,
This little patch add support to Canon MF230 Series scanner.
[bjnp] get_scanner_id: Scanner identity string =
MFG:CANON;CMD:MFNP1,MultiPASS 2.1;MDL:Canon MF230
Series;CLS:IMG;DES:Canon MF230 Series; - length = 88
[bjnp] get_scanner_id: Scanner model = Canon MF230 Series
Please commit.
Best regards
thierry
2017-05-19 09:26:25 UTC
Reply
Permalink
Raw Message
Hello,

It's could be out of topic for MF240, but all allowed resolutions
(75/150/300/600dpi) tested give me good results with the new supported
MF230 series (MF232w).

Regards
Post by thierry
Hello,
I just got a report from a MF240 Series scanner that only 300dpi is
possible (allowed) scanning from the document feeder. Please test this
and report your results.
Many thanks for your help in advance.
Cheers,
Rolf
Post by thierry
Hello,
I just committed the patch to the git repository (pixma backend
version >= 0.17.36) and updated the doc files. I also added the new
scanners i-SENSYS MF240 Series
Many thanks for your help.
Cheers,
Rolf
Post by thierry
Hello,
I also have a Canon ImageClass MF232.
I added that patch into the pixma_imageclass.c file, recompiled
the sane backeneds and it seems to work perfectly.
Thank You!
Post by thierry
Hello,
This little patch add support to Canon MF230 Series scanner.
[bjnp] get_scanner_id: Scanner identity string =
MFG:CANON;CMD:MFNP1,MultiPASS 2.1;MDL:Canon MF230
Series;CLS:IMG;DES:Canon MF230 Series; - length = 88
[bjnp] get_scanner_id: Scanner model = Canon MF230 Series
Please commit.
Best regards
--
sane-devel mailing list: sane-***@lists.alioth.debian.org
http://lists.alioth.debian.org/cgi-bin/mailman/listinfo/sane-devel
Unsubscribe: Send mail with subject "unsubscribe your_password"
to sane-devel-request
Loading...