Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

JP2000 returning OPJ_CLRSPC_UNKNOWN color space #1103

Closed
Jehan opened this issue Mar 4, 2018 · 27 comments
Closed

JP2000 returning OPJ_CLRSPC_UNKNOWN color space #1103

Jehan opened this issue Mar 4, 2018 · 27 comments

Comments

@Jehan
Copy link

Jehan commented Mar 4, 2018

Hi,

I came accross this image which is even in the external references on Wikipedia for the JPEG2000 format page: http://www.fnordware.com/j2k/jp2samples.html

When loading this file with OpenJPEG, the color space is OPJ_CLRSPC_UNKNOWN.
Is the JP2 file wrongly encoded or is there some feature missing in OpenJPEG?

For the background, we are currently porting our JPEG2000 support in GIMP to using OpenJPEG. This is where I came into this file when testing various reference images found on the web.

@boxerab
Copy link
Contributor

boxerab commented Mar 5, 2018

This image has an embedded ICC profile, so the colour space info is stored in the profile and is not specified elsewhere in the JPEG 2000 header. However, the ICC profile is corrupt, so it cannot be used. If you open this image with Kakadu kdu_show, the colours are messed up, due to corrupt ICC.

@Jehan
Copy link
Author

Jehan commented Mar 5, 2018

Ok. So basically, we should not try to support it. If GIMP cannot open this file, that is correct behavior, isn't it?
And it is normal that OpenJPEG returns OPJ_CLRSPC_UNKNOWN?

@boxerab
Copy link
Contributor

boxerab commented Mar 5, 2018

Yes, it is normal that OPJ_CLRSPC_UNKNOWN is returned. Not sure about the answers to your other questions.

@Jehan
Copy link
Author

Jehan commented Mar 5, 2018

Not sure about the answers to your other questions.

Well mostly wondering how a program should handle or display such a file.
Is there an acceptable fallback or is it just broken beyond repair? :-)

@szukw000
Copy link
Contributor

szukw000 commented Mar 5, 2018

@Jehan , @boxerab ,
gimp-2.8.22 shows the file relax.jp2 . IrfanView shows the file relax.jp2 .
animate shows the file relax.jp2 . Only kdu_show fails to show relax.jp2 .
winfried

@Jehan
Copy link
Author

Jehan commented Mar 5, 2018

gimp-2.8.22 shows the file relax.jp2.

For info, this was using Jasper, back in 2.8.x. GIMP 2.10 will stop being able to show this file as we are moving to OpenJPEG, hence the bug report.

@boxerab
Copy link
Contributor

boxerab commented Mar 5, 2018

Only kdu_show tries to apply the ICC profile, so it is the only program that has problems with this particular file. For Gimp, you will need to find a way of retrieving ICC from the compressed JPEG 2000 file. I don't think OpenJPEG currently does this. Or you could just ignore it. You can use a library like Little CMS to do a sanity check on the profile if you can extract it : in this case you would ignore the profile and just display the decompressed pixels as sRGB.

@Jehan
Copy link
Author

Jehan commented Mar 10, 2018

Ok. So what we do now in GIMP (current master) is that we determine the color space from the embedded ICC profile if it is not declared in the header. So now we can cleanly load this image, though the colors are indeed all fucked up, which is apparently normal since you said that the ICC profile is broken. We can get the proper image assuming some sRGB by just removing the profile.
Unless you think we are doing something wrong (hopefully not, since I followed what I understood from your indications), this issue can be considered solved, I guess.

I still have some questions regarding color spaces that I encountered for other images. Rather than opening other issues, I guess I can just ask here. :-)

(1) So I was opening your various openjpeg-data conformance images. I noticed that images in JPEG 2000 codestream in particular (.j2c) all have no color space declared, neither have they any ICC profile embedded. Reading more, I am guessing this may be normal. Do codestream files even have a header? From what I could gather, the codestream format may just be the compressed image data, whereas the JP2 format is more of a container which includes JP2 codestream.
So can't JP2 codestream files have any color space or profile information?

Right now, our code is stupid and will basically assume some Grayscale or RGB/RGBA, depending on the number of components, when there is no color space declared, nor profile, in such a file, but obviously this is not right, since JPEG2000 supports much more color spaces (CMYK, YUV, YCC…). So should we just pop-up a dialog asking for the user to select the right format? Or is there another way in the format to detect the right color space?

(2) Apart from the ugly "assuming RGB/Gray" spaces, GIMP is now able to load most of the .j2c files in conformance/ but for a6_mono_colr.j2c. We encountered here a case where some components did not have the same dimension (width, height) as the others. I am trying to understand what this means. Is this a RGB file? And if so, how can a component have different size as the others?
Or is it another kind of features of JPEG2000? If so, which?

I tried to look in tests/conformance/CMakeLists.txt and see that you are doing specific tests for this image, but I'm still unsure of its contents. It doesn't look like you have any document explaining what kind of data is in each file; this would be quite a useful document. :-)

@boxerab
Copy link
Contributor

boxerab commented Mar 10, 2018

@Jehan that sounds like an improvement if you are now looking at the ICC profile. But, you should be able to do a sanity check on the profile and determine that it is corrupt. Check out Little CMS - excellent little library, if you are able to add a dependency.

Yes, .j2k only stores the compressed code stream, so no colour information. A dialog would be appropriate here. You would need to handle alpha channels as well; also it is possible for the channels to be permuted i.e. the first channel of an RGB image may not be R. But this situation is probably pretty rare.

For a6_mono_colr.j2c, the channels are sub-sampled.
https://en.wikipedia.org/wiki/Chroma_subsampling

Jehan pushed a commit to GNOME/gimp that referenced this issue Mar 10, 2018
After moving up the profile extraction, I was running
gimp_image_set_color_profile() with a non-existing image id, which was
obviously wrong. Reorder a bit the operations.

Also try to guess the color space from the profile not only with
OPJ_CLRSPC_UNSPECIFIED but also OPJ_CLRSPC_UNKNOWN images. Indeed I
encountered a case of .jp2 image with no color space in the header, but
with an embedded profile. And unlike the .j2c files I encountered
earlier, the color space was now *_UNKNOWN.
See uclouvain/openjpeg#1103
@Jehan
Copy link
Author

Jehan commented Mar 10, 2018

that sounds like an improvement if you are now looking at the ICC profile

We were actually already extracting and applying the profile (GIMP is deeply color-managed nowadays, so applying the embedded profiles are something we do for every formats). We were simply not using it to determine the color space in JP2 since we were relying on the header data. The fact that sometimes the header data is not set is a bit weird. Anyway…

Check out Little CMS - excellent little library, if you are able to add a dependency.

We already have a mandatory dependency to lcms2 (as I said, we are deeply color-managed in every piece of code). I'll have a look if there is anything in lcms2 API to detect the corruption but we actually already create a lcms profile with this data, and we get zero complaint from lcms with the profile embedded in this image.
I'll have a closer look at lcms2 API to see if there are other functions to detect the corruption, but so far I could not find any.

For a6_mono_colr.j2c, the channels are sub-sampled.

Thanks. We'll try to have a closer look at this.

@boxerab
Copy link
Contributor

boxerab commented Mar 10, 2018

Cool. When I run the (C++11) code below on the ICC profile for that image, I get bufferSize equal to zero. I take this as a sign that the profile is corrupt.

if (image->icc_profile_buf && image->icc_profile_len)	{
	auto in_prof = cmsOpenProfileFromMem(image->icc_profile_buf, image->icc_profile_len);
	if (in_prof) {
		cmsUInt32Number bufferSize = cmsGetProfileInfo(in_prof, cmsInfoDescription, cmsNoLanguage, cmsNoCountry, nullptr, 0);
		if (bufferSize) {
                             //read profile name
                     }
            }
   }

@boxerab
Copy link
Contributor

boxerab commented Mar 10, 2018

So, it looks like the description tag is missing. I am not sure if this is a mandatory tag for a well-formed profile. If not mandatory, then this does not actually indicate profile corruption. You may then have to apply the profile.

@Jehan
Copy link
Author

Jehan commented Mar 10, 2018

So, it looks like the description tag is missing. I am not sure if this is a mandatory tag for a well-formed profile. If not mandatory, then this does not actually indicate profile corruption. You may then have to apply the profile.

Yeah I was wondering the same thing, and looking through lcms code to determine if that were really mandatory. Maybe I'll open a bug report at lcms and ask them if this profile is really considered corrupted for them, and if so, how do we determine this (and also maybe cmsOpenProfileFromMem() should return NULL directly in that case).

@boxerab
Copy link
Contributor

boxerab commented Mar 12, 2018

By the way, when trying to decompress this file to png, libpng complains that this ICC profile has an invalid rendering intent (intent equals 0x10000 ). So, this may be a clue that the ICC profile is invalid.

@Jehan
Copy link
Author

Jehan commented Mar 19, 2018

So I encountered cases where the JP2 header had no color space, but the color space information was there through an ICC profile. And apparently J2K files never have neither header nor ICC profile.

Can there also be a JP2 with no color space defined in the header nor any ICC profile as well? Or are JP2 always expected to have one or the other?

@boxerab
Copy link
Contributor

boxerab commented Mar 19, 2018

JP2 will have a colour space defined.

@Jehan
Copy link
Author

Jehan commented Mar 20, 2018

So I am trying to figure out the best user-visible names for color spaces in the dialog when opening a JP2 codestream but I am a bit unsure.
I was relying on the comment part of the enum:

OPJ_CLRSPC_SYCC = 3, /< YUV */
OPJ_CLRSPC_EYCC = 4, /
< e-YCC */

So I was calling them YUV and e-YCC.

First for YUV, reading Wikipedia I wonder if Y'UV is not actually the most common naming for the color space. Also I can't help but notice that the enum is *_SYCC. Searching Wikipedia again, I find this info:

Amendment A1:2003 to IEC 61966-2-1:1999 describes an analogous sYCC encoding for YCbCr color spaces, an extended-gamut RGB encoding, and a CIELAB transformation.

So should it actually be sYCC?

As for e-YCC, I just cannot find any reference of it anywhere (under e-YCC or eYCC or anything). Is there maybe a more common name for this color space?

Sorry for all the (probably) stupid questions, but this is so hard to find information for these by not being freely published standards (actually more searches I do for these 2 color spaces basically return me links to OpenJPEG!).

@boxerab
Copy link
Contributor

boxerab commented Mar 20, 2018

I think s refers to standard YCC, and e refers to extended YCC.

@Jehan
Copy link
Author

Jehan commented Apr 3, 2018

Thanks @boxerab for all the help. Our support in GIMP 2.10 will be much better already (only import for now though) and I guess what we have right now is ok. I'll close this report.
If I have more issues/questions, I can always open a new one. :-)

@Jehan Jehan closed this as completed Apr 3, 2018
@boxerab
Copy link
Contributor

boxerab commented Apr 3, 2018

np, looking forward to trying out the new version when it gets unleashed.

@jubalh
Copy link

jubalh commented Apr 16, 2019

Sorry for commenting on such an old issue. Just have a question about it.

For porting some application from jasper to digikam I read GIMPs code, as an example.

@Jehan how comes that GIMP displays http://www.fnordware.com/j2k/jp2samples.html for a split second correctly and then displays it weirdly (green)? I understood it like the corrupted color profile makes you not really support it but don't get how it can display it 'correctly' at first.

And may I ask which example JPEG2000 you used instead for testing?

@Jehan
Copy link
Author

Jehan commented Apr 16, 2019

@jubalh

@Jehan how comes that GIMP displays http://www.fnordware.com/j2k/jp2samples.html for a split second correctly and then displays it weirdly (green)?

Probably you see it fine for this split second before the profile is applied.
As I explained in an early comment, the way to see an acceptable image is by loading the image while keeping the profile (don't "convert" to GIMP built-in sRGB), then go to Image > Color management > Discard Color Profile. Then you get something with believable colors. This file's embedded profile is just broken beyond measures.

And may I ask which example JPEG2000 you used instead for testing?

This is like eons ago. I have no idea what other files I may have used. I remember I used a bunch of files, though this format doesn't have that many samples around. If I recall, the OpenJPEG project must also have some sample files in a repository.

@jubalh
Copy link

jubalh commented Apr 16, 2019

@Jehan thanks!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

5 participants
@boxerab @Jehan @jubalh @szukw000 and others