Fwd: ImageJ reads reversed bits from unsigned 16-bit TIFF saved by imwrite() from GNU Octave.

Previous Topic Next Topic
 
classic Classic list List threaded Threaded
4 messages Options
Reply | Threaded
Open this post in threaded view
|

Fwd: ImageJ reads reversed bits from unsigned 16-bit TIFF saved by imwrite() from GNU Octave.

Carnë Draug
On 3 November 2014 11:05, Pariksheet Nanda <[hidden email]> wrote:

> Hi all,
>
> ImageJ shows pixel values different from those saved by GNU Octave.
> The byte positions are the same, the bits within each byte are
> reversed, so I'm not sure if this is a traditional problem of
> endianness?  For example the value 274 saved from the Octave matrix
> appears as 32480 in ImageJ; the binary representations of which are
> below:
>
> Number saved by Octave (decimal 274):  01001000 10000000
> Number read by ImageJ (decimal 32840): 00010010 00000001
>
> 1) Can anyone else reproduce this problem?  At the end of this e-mail
> is the code for Octave to generate the image stacks, and an ImageJ
> macro that reads the value of each slice (or frame), and shows the
> binary and expected values in the results window.  Also the image
> stacks from Octave are uploaded here and compressed to 7 kb; password
> is imagej
> https://filelocker.uconn.edu/public_download?shareId=2c8c0c3141741de36547a9db46b1f06c
>
> 2) Can you help me identify where the problem might be coming from?
> GNU Octave has a wrapper for ImageMagick C++ interface, which in turn
> uses libtiff.  Perhaps the next logical thing would be to inspect the
> binary values from the TIFF file or check the TIFF file headers, etc
> but I'm not sure how to approach those investigations.  My application
> and library versions are:
>
> - ImageJ 1.49i (bundled with FIJI linux-32)
> - Octave 3.8.2
> - ImageMagick 6.8.8.10
> - libtiff 4.0.3

I can't replicate this using Octave 3.8.2 on Debian Jessie with
GraphicsMagick 1.3.20 (quantum 16) and libtiff 4.0.3.

Since Octave does not distribute binaries (and certainly not GraphicsMagick
or ImageMagick binaries), how did you install it? Did you build it from
source or are you using the one from the repositories? And are you sure it's
wrapping ImageMagick and not GraphicsMagick?
Run 'octave_config_info ("MAGICK_LIBS")' at the Octave prompt and

ldd $(octave -qf --eval 'printf (which ("__magick_read__"))') | grep Magick

from bash?

Also, does Octave reads the "bad.tif" file it generates correctly?

> 3) Are there any Octave + ImageJ users out there?  How do you export
> images from Octave for ImageJ?  Also do you interface Octave data with
> ImageJ / FIJI using the Java Octave Forge package?
>
> [...]

The Java package is included in Octave core since 3.8.0. If you are still
using the java package you are shadowing the builtin functions.

Carnë

--
ImageJ mailing list: http://imagej.nih.gov/ij/list.html
Reply | Threaded
Open this post in threaded view
|

Re: ImageJ reads reversed bits from unsigned 16-bit TIFF saved by imwrite() from GNU Octave.

Pariksheet Nanda
Hi Carnë,

On Tue, Nov 4, 2014 at 10:42 AM, Carnë Draug <[hidden email]> wrote:

> On 3 November 2014 11:05, Pariksheet Nanda <[hidden email]> wrote:
>> Hi all,
>>
>> ImageJ shows pixel values different from those saved by GNU Octave.
>> The byte positions are the same, the bits within each byte are
>> reversed
>>
>> [...]
>>
>> 2) Can you help me identify where the problem might be coming from?
>> GNU Octave has a wrapper for ImageMagick C++ interface, which in turn
>> uses libtiff.  Perhaps the next logical thing would be to inspect the
>> binary values from the TIFF file or check the TIFF file headers, etc
>> but I'm not sure how to approach those investigations.  My application
>> and library versions are:
>>
>> - ImageJ 1.49i (bundled with FIJI linux-32)
>> - Octave 3.8.2
>> - ImageMagick 6.8.8.10
>> - libtiff 4.0.3
>
> I can't replicate this using Octave 3.8.2 on Debian Jessie with
> GraphicsMagick 1.3.20 (quantum 16) and libtiff 4.0.3.

I think you might have missed Michael's and Curtis' resposes in this
thread.  As Curtis suggested, the cause of the bit reversal was due to
FillOrder TIFF tag being set to <2> i.e. reverse order:
http://imagej.1557.x6.nabble.com/ImageJ-reads-reversed-bits-from-unsigned-16-bit-TIFF-saved-by-imwrite-from-GNU-Octave-tp5010285p5010291.html
You can check for the FillOrder tag in the Multi-TIFF files with
`tiffdump'.  In all likelihood your GraphicsMagick setup either does
not create this tag and thus per the Adobe TIFF6 specification it
defaults to a value of <1> for normal FillOrder.


> Since Octave does not distribute binaries (and certainly not GraphicsMagick
> or ImageMagick binaries), how did you install it? Did you build it from
> source or are you using the one from the repositories?

I'm using Gentoo GNU/Linux, so ImageMagick (not GraphicsMagick) is
pulled in and installed by the package manager, portage [5].  It's
built from source.


> And are you sure it's
> wrapping ImageMagick and not GraphicsMagick?

I only have ImageMagick installed and not GraphicsMagik [6].


> Run 'octave_config_info ("MAGICK_LIBS")' at the Octave prompt and

Here's the output

   octave:1> octave_config_info ("MAGICK_LIBS")
   ans = -lMagick++-6.Q16 -lMagickWand-6.Q16 -lMagickCore-6.Q16


> ldd $(octave -qf --eval 'printf (which ("__magick_read__"))') | grep Magick
>
> from bash?

   omsai@xm2 ~ $ ldd $(octave -qf --eval 'printf (which
("__magick_read__"))') | grep Magick
       libMagick++-6.Q16.so.3 => /usr/lib/libMagick++-6.Q16.so.3 (0xb5900000)
       libMagickCore-6.Q16.so.2 => /usr/lib/libMagickCore-6.Q16.so.2
(0xb5646000)
       libMagickWand-6.Q16.so.2 => /usr/lib/libMagickWand-6.Q16.so.2
(0xb40dd000)


> Also, does Octave reads the "bad.tif" file it generates correctly?

Yes, it reads it in correctly per imread ('/tmp/bad.tif'. 'Frames', 'all')


>> 3) Are there any Octave + ImageJ users out there?  How do you export
>> images from Octave for ImageJ?  Also do you interface Octave data with
>> ImageJ / FIJI using the Java Octave Forge package?
>>
>> [...]
>
> The Java package is included in Octave core since 3.8.0. If you are still
> using the java package you are shadowing the builtin functions.

Excellent, thanks for explaining; I'll poke around it some time.


> Carnë

Pariksheet


[5]
omsai@xm2 ~ $ equery depgraph octave
 * Searching for octave ...

 * dependency graph for sci-mathematics/octave-3.8.2
 `--  sci-mathematics/octave-3.8.2  ~x86
   `--  app-text/ghostscript-gpl-9.10-r2  (app-text/ghostscript-gpl) x86
   `--  dev-libs/libpcre-8.35  (dev-libs/libpcre) x86
   `--  sys-libs/ncurses-5.9-r3  (sys-libs/ncurses) x86
   `--  virtual/lapack-3.1  (virtual/lapack) x86
   `--  net-misc/curl-7.37.1  (net-misc/curl) x86
   `--  sci-libs/fftw-3.3.3-r2  (sci-libs/fftw) x86
   `--  sci-mathematics/glpk-4.45  (sci-mathematics/glpk) x86
   `--  sci-visualization/gnuplot-4.6.5  (sci-visualization/gnuplot) x86
   `--  x11-libs/qscintilla-2.7.2  (x11-libs/qscintilla) x86
   `--  sci-libs/hdf5-1.8.10  (sci-libs/hdf5) x86
   `--  media-gfx/graphicsmagick-1.3.18  (media-gfx/graphicsmagick) x86  [cxx]
   `--  media-gfx/imagemagick-6.8.9.9  (media-gfx/imagemagick) x86  [cxx]
   `--  virtual/jre-1.6.0-r1  (>=virtual/jre-1.6.0) x86
   `--  sys-devel/llvm-3.3-r3  (<sys-devel/llvm-3.5) x86
   `--  media-libs/freetype-2.5.3-r1  (media-libs/freetype) x86
   `--  media-libs/fontconfig-2.10.92  (media-libs/fontconfig) x86
   `--  x11-libs/fltk-1.3.2  (>=x11-libs/fltk-1.3) x86  [opengl]
   `--  x11-libs/gl2ps-1.3.6  (x11-libs/gl2ps) x86
   `--  virtual/glu-9.0-r1  (virtual/glu) x86
   `--  app-text/epstool-3.08-r1  (app-text/epstool) x86
   `--  media-gfx/pstoedit-3.61  (media-gfx/pstoedit) x86
   `--  media-gfx/transfig-3.2.5d-r1  (media-gfx/transfig) x86
   `--  media-libs/qhull-2012.1-r1  (media-libs/qhull) x86
   `--  sci-libs/qrupdate-1.1.0  (sci-libs/qrupdate) x86
   `--  sys-libs/readline-6.2_p5-r1  (sys-libs/readline) x86
   `--  sci-libs/arpack-0.96-r3  (sci-libs/arpack) x86
   `--  sci-libs/camd-2.2.0  (sci-libs/camd) x86
   `--  sci-libs/ccolamd-2.7.3  (sci-libs/ccolamd) x86
   `--  sci-libs/cholmod-1.6.0-r1  (sci-libs/cholmod) x86
   `--  sci-libs/colamd-2.7.3  (sci-libs/colamd) x86
   `--  sci-libs/cxsparse-2.2.1  (sci-libs/cxsparse) x86
   `--  sci-libs/umfpack-5.2.0  (sci-libs/umfpack) x86
   `--  x11-libs/libX11-1.6.2  (x11-libs/libX11) x86
   `--  sys-libs/zlib-1.2.8-r1  (sys-libs/zlib) x86
   `--  app-misc/pax-utils-0.8.1  (app-misc/pax-utils) x86
   `--  virtual/jdk-1.6.0-r2  (>=virtual/jdk-1.6.0) x86
   `--  virtual/latex-base-1.0  (virtual/latex-base) x86
   `--  dev-texlive/texlive-genericrecommended-2012
(dev-texlive/texlive-genericrecommended) x86
   `--  dev-texlive/texlive-metapost-2012  (dev-texlive/texlive-metapost) x86
   `--  sys-apps/texinfo-4.13-r2  (sys-apps/texinfo) x86
   `--  dev-util/gperf-3.0.4  (dev-util/gperf) x86
   `--  virtual/pkgconfig-0-r1  (virtual/pkgconfig) x86
   `--  sys-devel/automake-1.13.4  (>=sys-devel/automake-1.13) x86
   `--  sys-devel/automake-1.14.1  (>=sys-devel/automake-1.14) [~x86 keyword]
   `--  sys-devel/autoconf-2.69  (>=sys-devel/autoconf-2.69) x86
   `--  sys-devel/libtool-2.4.2-r1  (sys-devel/libtool) x86
   `--  virtual/fortran-0  (virtual/fortran) x86
   `--  dev-java/java-config-2.2.0  (>=dev-java/java-config-2.1.9-r1) x86
[ sci-mathematics/octave-3.8.2 stats: packages (49), max depth (1) ]


[6]
omsai@xm2 ~ $ eix imagemagick
[U] media-gfx/imagemagick
     Available versions:  6.8.8.10-r1(0/6.8.8.10)^u
~6.8.9.7(0/6.8.9.7)^u ~6.8.9.8(0/6.8.9.8)^u 6.8.9.9(0/6.8.9.9)^u {X
autotrace bzip2 corefonts cxx djvu fftw fontconfig fpx graphviz hdri
jbig jpeg jpeg2k lcms lqr lzma opencl openexr openmp pango perl png
postscript q32 q64 q8 raw static-libs svg test tiff truetype webp wmf
xml zlib}
     Installed versions:  6.8.8.10-r1(06:06:02 PM 08/11/2014)(X bzip2
cxx jpeg lcms openmp pango png svg tiff truetype xml zlib -autotrace
-corefonts -djvu -fftw -fontconfig -fpx -graphviz -hdri -jbig -jpeg2k
-lqr -lzma -opencl -openexr -perl -postscript -q32 -q64 -q8 -raw
-static-libs -test -webp -wmf)
     Homepage:            http://www.imagemagick.org/
     Description:         A collection of tools and libraries for many
image formats

omsai@xm2 ~ $ eix graphicsmagick
* media-gfx/graphicsmagick
     Available versions:  1.3.18 ~1.3.19 ~1.3.20-r1 {X bzip2 cxx debug
fpx imagemagick jbig jpeg jpeg2k lcms lzma modules openmp perl png
postscript q16 q32 static-libs svg threads tiff truetype webp wmf
zlib}
     Homepage:            http://www.graphicsmagick.org/
     Description:         Collection of tools and libraries for many
image formats

--
ImageJ mailing list: http://imagej.nih.gov/ij/list.html
Reply | Threaded
Open this post in threaded view
|

Re: ImageJ reads reversed bits from unsigned 16-bit TIFF saved by imwrite() from GNU Octave.

Carnë Draug
On 4 November 2014 17:57, Pariksheet Nanda <[hidden email]> wrote:

> Hi Carnë,
>
> On Tue, Nov 4, 2014 at 10:42 AM, Carnë Draug <[hidden email]> wrote:
>> On 3 November 2014 11:05, Pariksheet Nanda <[hidden email]> wrote:
>>> Hi all,
>>>
>>> ImageJ shows pixel values different from those saved by GNU Octave.
>>> The byte positions are the same, the bits within each byte are
>>> reversed
>>>
>>> [...]
>>>
>>> 2) Can you help me identify where the problem might be coming from?
>>> GNU Octave has a wrapper for ImageMagick C++ interface, which in turn
>>> uses libtiff.  Perhaps the next logical thing would be to inspect the
>>> binary values from the TIFF file or check the TIFF file headers, etc
>>> but I'm not sure how to approach those investigations.  My application
>>> and library versions are:
>>>
>>> - ImageJ 1.49i (bundled with FIJI linux-32)
>>> - Octave 3.8.2
>>> - ImageMagick 6.8.8.10
>>> - libtiff 4.0.3
>>
>> I can't replicate this using Octave 3.8.2 on Debian Jessie with
>> GraphicsMagick 1.3.20 (quantum 16) and libtiff 4.0.3.
>
> I think you might have missed Michael's and Curtis' resposes in this
> thread.  As Curtis suggested, the cause of the bit reversal was due to
> FillOrder TIFF tag being set to <2> i.e. reverse order:
> http://imagej.1557.x6.nabble.com/ImageJ-reads-reversed-bits-from-unsigned-16-bit-TIFF-saved-by-imwrite-from-GNU-Octave-tp5010285p5010291.html
> You can check for the FillOrder tag in the Multi-TIFF files with
> `tiffdump'.  In all likelihood your GraphicsMagick setup either does
> not create this tag and thus per the Adobe TIFF6 specification it
> defaults to a value of <1> for normal FillOrder.

I see the now on nabble. I'm only subscribed to the daily digest and will
only get their emails tomorrow morning.

> Since ImageJ2 handles Fill Order in reading the image, I'll ask the
> Octave folks if they intended to use the esoteric Fill Order type <2>.

According to libtiff documentation, you can specify FILLORDER when building
libtiff [7].  Octave itself relies on GraphicsMagick (or ImageMagick) to make
the right choice and they rely on libtiff.

Octave itself does not touch that option (there's not even a method to
set it from GraphicsMagick's C++ interface *) so you won't be able to specify
this from Octave.  But if I understood correctly, libtiff is acting correctly
and saving the file as configured, it's ImageJ1 that is ignoring this tag
and reading the file wrong, and this is already fixed if you are using SCIFIO.

You should be able to fix this by rebuilding libtiff with different flags.

Searching online, some people seem to also had success by running ImageMagick
convert tool on the generated image (which would imply a system() on your
code after writing the image).

Carnë

[7] http://www.libtiff.org/build.html

* there seems to be an undocumented way to do this. Looking at the source of
ImageMagick tiff coder there's an atribute with this value (this will return
nothing on GraphicsMagick and I do not know the ImageMagick version where it
was added).  If the following works when reading a file, it may work to set
the attribute before writing.

#include <Magick++.h>
#include <iostream>

int
main (int argc, char **argv)
{
  if (argc < 2)
    return 1;

  Magick::InitializeMagick (*argv);
  Magick::Image image (argv[1]);
  std::cout << image.attribute ("tiff:fill-order") << std::endl;
  return 0;
}

--
ImageJ mailing list: http://imagej.nih.gov/ij/list.html
Reply | Threaded
Open this post in threaded view
|

Re: ImageJ reads reversed bits from unsigned 16-bit TIFF saved by imwrite() from GNU Octave.

Pariksheet Nanda
Hi Carnë,

On Tue, Nov 4, 2014 at 7:33 PM, Carnë Draug <[hidden email]> wrote:

>
> On 4 November 2014 17:57, Pariksheet Nanda <[hidden email]> wrote:
>>
>> Since ImageJ2 handles Fill Order in reading the image, I'll ask the
>> Octave folks if they intended to use the esoteric Fill Order type <2>.
>
> According to libtiff documentation, you can specify FILLORDER when building
> libtiff [7].  Octave itself relies on GraphicsMagick (or ImageMagick) to make
> the right choice and they rely on libtiff.
>
> [...]
>
> But if I understood correctly, libtiff is acting correctly
> and saving the file as configured, it's ImageJ1 that is ignoring this tag
> and reading the file wrong, and this is already fixed if you are using SCIFIO.
>
> You should be able to fix this by rebuilding libtiff with different flags.

To get the same results as you, I had to install GraphicsMagick 1.3.18
and recompile Octave 3.8.2 configuring it -with-magick=GraphicsMagick

Unlike ImageMagick, GraphicsMagick does not invert the bits or write a
FillOrder tag.

libtiff no longer supports a configure argument changing FILLORDER
since it has been replaced by HOST_FILLORDER [8] and neither does the
Debian package for libtiff 4.0.3, you are using, patch [9] or modify
the variable [10].  The libtiff build page [7] is quite out of date
(last updated in 2003 in the page footer), and probably explains why
FillOrder is not user configurable.

Since there's little further relevance to ImageJ at this point, I'll
consider this thread closed.  Thanks for everyone's help in narrowing
this down.


> Searching online, some people seem to also had success by running ImageMagick
> convert tool on the generated image (which would imply a system() on your
> code after writing the image).

I had tried `convert' and `mogrify' utilities, and besides needing
scripting to work with multi-TIFF, they are too smart for their own
good: for example `covert' changed several other TIFF tags like bit
depth.


> Carnë

Pariksheet

[8] There is HOST_FILLORDER, in ./configure.ac which just uses the
operating system endianness and there is also a definition for
HOST_BIGENDIAN.
[9] http://sources.debian.net/src/tiff/4.0.3-10/debian/patches/
[10] http://sources.debian.net/src/tiff/4.0.3-10/debian/rules/

--
ImageJ mailing list: http://imagej.nih.gov/ij/list.html