linux-media.vger.kernel.org archive mirror
 help / color / mirror / Atom feed
* [PATCH 00/28] bug fixes, additions, changes
@ 2021-09-24 23:31 joevt
  2021-09-24 23:31 ` [PATCH 01/28] edid-decode: remove unnecessary length check joevt
                   ` (19 more replies)
  0 siblings, 20 replies; 21+ messages in thread
From: joevt @ 2021-09-24 23:31 UTC (permalink / raw)
  To: Hans Verkuil; +Cc: linux-media

- Patch 02/28 replaces my previous patch 05/11.
It adds a new warning message.

- The problem with my previous patch 07/11 is addressed in patch 01/28 and 04/28 (and maybe elsewhere).

- Patches 06/28 to 26/28 replace my previous patch 11/11 (broken down into smaller steps this time).
They contain some corrections.

- Includes some other changes.


joevt (28):
  edid-decode: remove unnecessary length check
  edid-decode: fix standard timing vertical pixels
  edid-decode: exclude oui from _block functions
  edid-decode: check cta_hdr10plus length
  edid-decode: Capitalize fail sentence
  edid-decode: Replace return with break in switch
  edid-decode: extended tag length check
  edid-decode: Output block type before fail
  edid-decode: update Microsoft expected length
  edid-decode: Capitalize fail sentence
  edid-decode: make all OUI handlers the same
  edid-decode: move OUI parsing to separate function
  edid-decode: move unknown block warning
  edid-decode: remove cta_ext_block
  edid-decode: change unknown CTA block names
  edid-decode: move audio fail/warn messages
  edid-decode: replace first_block with block_number
  edid-decode: move parse_displayid_block inner loop
  edid-decode: remove offset from displayid_block
  edid-decode: displayid_block len fixes
  edid-decode: ignore DisplayID version for OUI check.
  edid-decode: DisplayID non-0 filler fixes
  edid-decode: DisplayID length checks
  edid-decode: make OUI enum
  edid-decode: more OUI changes
  edid-decode: remove extra vendor field
  edid-decode: re-add one EDID
  edid-decode: add interesting EDID

 data/apple-imac-retina-4k-21.5-inch-late-2015 | Bin 0 -> 256 bytes
 data/vizio-m60c3-hdmi-onkyo-txnr555           | Bin 0 -> 256 bytes
 edid-decode.cpp                               | 106 +++-
 edid-decode.h                                 |  32 +-
 oui.h                                         |  20 +
 parse-base-block.cpp                          |   5 +-
 parse-cta-block.cpp                           | 482 +++++++----------
 parse-displayid-block.cpp                     | 498 +++++++++---------
 8 files changed, 553 insertions(+), 590 deletions(-)
 create mode 100644 data/apple-imac-retina-4k-21.5-inch-late-2015
 create mode 100644 oui.h

-- 
2.24.3 (Apple Git-128)


^ permalink raw reply	[flat|nested] 21+ messages in thread

* [PATCH 01/28] edid-decode: remove unnecessary length check
  2021-09-24 23:31 [PATCH 00/28] bug fixes, additions, changes joevt
@ 2021-09-24 23:31 ` joevt
  2021-09-24 23:31 ` [PATCH 02/28] edid-decode: fix standard timing vertical pixels joevt
                   ` (18 subsequent siblings)
  19 siblings, 0 replies; 21+ messages in thread
From: joevt @ 2021-09-24 23:31 UTC (permalink / raw)
  To: Hans Verkuil; +Cc: linux-media

The for loop also checks the length. Nothing will happen if length is zero as expected.

Signed-off-by: Joe van Tunen <joevt@shaw.ca>
---
 edid-decode.cpp | 3 ---
 1 file changed, 3 deletions(-)

diff --git a/edid-decode.cpp b/edid-decode.cpp
index d5062dd..d77646d 100644
--- a/edid-decode.cpp
+++ b/edid-decode.cpp
@@ -700,9 +700,6 @@ void hex_block(const char *prefix, const unsigned char *x,
 {
 	unsigned i, j;
 
-	if (!length)
-		return;
-
 	for (i = 0; i < length; i += step) {
 		unsigned len = min(step, length - i);
 
-- 
2.24.3 (Apple Git-128)


^ permalink raw reply related	[flat|nested] 21+ messages in thread

* [PATCH 02/28] edid-decode: fix standard timing vertical pixels
  2021-09-24 23:31 [PATCH 00/28] bug fixes, additions, changes joevt
  2021-09-24 23:31 ` [PATCH 01/28] edid-decode: remove unnecessary length check joevt
@ 2021-09-24 23:31 ` joevt
  2021-09-24 23:31 ` [PATCH 03/28] edid-decode: exclude oui from _block functions joevt
                   ` (17 subsequent siblings)
  19 siblings, 0 replies; 21+ messages in thread
From: joevt @ 2021-09-24 23:31 UTC (permalink / raw)
  To: Hans Verkuil; +Cc: linux-media

Don't do ceiling to nearest 8 pixels for active vertical lines. See examples elo-4600l-hdmi and kogan-kaled24144f-hdmi.

Section 3.9 and 3.10.3.6 of EDID 1.4 does not say vertical lines must be a multiple of 8.  This line of code appears to have been added to satisfy the 3rd example in VTB-EXT spec but that example has an incorrect HAP indicator decimal value so it cannot be trusted. Also, all 3 examples have an incorrect vertical refresh value as noted in parse-vtb-ext-block.cpp. The VESA DMT spec has the following examples that are not a multiple of 8 lines which support this change:
1400x1050 4:3
1440x900 16:10
1600x900 16:9
1680x1050 16:10

Finally, Ref. D-8 of EDID 1.4 says about Section 3.9 that "The Standard Timings Identification code may not be used to identify timings which do not match one of these standard aspect ratios."

If vertical lines is odd then a warning is output. That way an attempt to use ST to describe 1360x768 (a common resolution) will result in a warning (since the nearest result that can be described by an ST is 1360x765).

Signed-off-by: Joe van Tunen <joevt@shaw.ca>
---
 parse-base-block.cpp | 5 ++++-
 1 file changed, 4 insertions(+), 1 deletion(-)

diff --git a/parse-base-block.cpp b/parse-base-block.cpp
index 174af51..dd56eed 100644
--- a/parse-base-block.cpp
+++ b/parse-base-block.cpp
@@ -573,7 +573,6 @@ void edid_state::print_standard_timing(const char *prefix, unsigned char b1, uns
 		break;
 	}
 	vact = (double)hact * vratio / hratio;
-	vact = 8 * ((vact + 7) / 8);
 	refresh = (b2 & 0x3f) + 60;
 
 	formula.hact = hact;
@@ -605,6 +604,10 @@ void edid_state::print_standard_timing(const char *prefix, unsigned char b1, uns
 		min_vert_freq_hz = min(min_vert_freq_hz, refresh);
 		max_vert_freq_hz = max(max_vert_freq_hz, refresh);
 	}
+
+	// See Ref. D-8 in the EDID-1.4 spec
+	if (vact & 1)
+		warn("Standard Timing %ux%u has a dubious odd vertical resolution.\n", hact, vact);
 }
 
 void edid_state::detailed_display_range_limits(const unsigned char *x)
-- 
2.24.3 (Apple Git-128)


^ permalink raw reply related	[flat|nested] 21+ messages in thread

* [PATCH 03/28] edid-decode: exclude oui from _block functions
  2021-09-24 23:31 [PATCH 00/28] bug fixes, additions, changes joevt
  2021-09-24 23:31 ` [PATCH 01/28] edid-decode: remove unnecessary length check joevt
  2021-09-24 23:31 ` [PATCH 02/28] edid-decode: fix standard timing vertical pixels joevt
@ 2021-09-24 23:31 ` joevt
  2021-09-24 23:31 ` [PATCH 04/28] edid-decode: check cta_hdr10plus length joevt
                   ` (16 subsequent siblings)
  19 siblings, 0 replies; 21+ messages in thread
From: joevt @ 2021-09-24 23:31 UTC (permalink / raw)
  To: Hans Verkuil; +Cc: linux-media

cta_hdmi_block is the only function that has oui included. Make it like all the other functions by increasing x by 3 (the size of the oui) and decreasing length by the same amount.

Signed-off-by: Joe van Tunen <joevt@shaw.ca>
---
 parse-cta-block.cpp | 48 ++++++++++++++++++++++-----------------------
 1 file changed, 24 insertions(+), 24 deletions(-)

diff --git a/parse-cta-block.cpp b/parse-cta-block.cpp
index 4edaa1d..cee51d7 100644
--- a/parse-cta-block.cpp
+++ b/parse-cta-block.cpp
@@ -652,57 +652,57 @@ void edid_state::cta_hdmi_block(const unsigned char *x, unsigned length)
 {
 	unsigned len_vic, len_3d;
 
-	if (length < 4) {
+	if (length < 1) {
 		fail("Empty Data Block with length %u.\n", length);
 		return;
 	}
-	printf("    Source physical address: %x.%x.%x.%x\n", x[3] >> 4, x[3] & 0x0f,
-	       x[4] >> 4, x[4] & 0x0f);
+	printf("    Source physical address: %x.%x.%x.%x\n", x[0] >> 4, x[0] & 0x0f,
+	       x[1] >> 4, x[1] & 0x0f);
 
-	if (length < 6)
+	if (length < 3)
 		return;
 
-	if (x[5] & 0x80)
+	if (x[2] & 0x80)
 		printf("    Supports_AI\n");
-	if (x[5] & 0x40)
+	if (x[2] & 0x40)
 		printf("    DC_48bit\n");
-	if (x[5] & 0x20)
+	if (x[2] & 0x20)
 		printf("    DC_36bit\n");
-	if (x[5] & 0x10)
+	if (x[2] & 0x10)
 		printf("    DC_30bit\n");
-	if (x[5] & 0x08)
+	if (x[2] & 0x08)
 		printf("    DC_Y444\n");
 	/* two reserved bits */
-	if (x[5] & 0x01)
+	if (x[2] & 0x01)
 		printf("    DVI_Dual\n");
 
-	if (length < 7)
+	if (length < 4)
 		return;
 
-	printf("    Maximum TMDS clock: %u MHz\n", x[6] * 5);
-	if (x[6] * 5 > 340)
+	printf("    Maximum TMDS clock: %u MHz\n", x[3] * 5);
+	if (x[3] * 5 > 340)
 		fail("HDMI VSDB Max TMDS rate is > 340.\n");
 
-	if (length < 8)
+	if (length < 5)
 		return;
 
-	if (x[7] & 0x0f) {
+	if (x[4] & 0x0f) {
 		printf("    Supported Content Types:\n");
-		if (x[7] & 0x01)
+		if (x[4] & 0x01)
 			printf("      Graphics\n");
-		if (x[7] & 0x02)
+		if (x[4] & 0x02)
 			printf("      Photo\n");
-		if (x[7] & 0x04)
+		if (x[4] & 0x04)
 			printf("      Cinema\n");
-		if (x[7] & 0x08)
+		if (x[4] & 0x08)
 			printf("      Game\n");
 	}
 
-	unsigned b = 8;
-	if (x[7] & 0x80) {
+	unsigned b = 5;
+	if (x[4] & 0x80) {
 		hdmi_latency(x[b], x[b + 1], false);
 
-		if (x[7] & 0x40) {
+		if (x[4] & 0x40) {
 			if (x[b] == x[b + 2] &&
 			    x[b + 1] == x[b + 3])
 				warn("Progressive and Interlaced latency values are identical, no need for both.\n");
@@ -712,7 +712,7 @@ void edid_state::cta_hdmi_block(const unsigned char *x, unsigned length)
 		b += 2;
 	}
 
-	if (!(x[7] & 0x20))
+	if (!(x[4] & 0x20))
 		return;
 
 	bool mask = false;
@@ -2212,7 +2212,7 @@ void edid_state::cta_block(const unsigned char *x, bool duplicate)
 			fail((std::string("OUI ") + ouitohex(oui) + " is in the wrong byte order\n").c_str());
 		printf("  %s, OUI %s:\n", data_block.c_str(), ouitohex(oui).c_str());
 		if (oui == 0x000c03) {
-			cta_hdmi_block(x + 1, length);
+			cta_hdmi_block(x + 4, length - 3);
 			cta.last_block_was_hdmi_vsdb = 1;
 			cta.first_block = 0;
 			// The HDMI OUI is present, so this EDID represents an HDMI
-- 
2.24.3 (Apple Git-128)


^ permalink raw reply related	[flat|nested] 21+ messages in thread

* [PATCH 04/28] edid-decode: check cta_hdr10plus length
  2021-09-24 23:31 [PATCH 00/28] bug fixes, additions, changes joevt
                   ` (2 preceding siblings ...)
  2021-09-24 23:31 ` [PATCH 03/28] edid-decode: exclude oui from _block functions joevt
@ 2021-09-24 23:31 ` joevt
  2021-09-24 23:31 ` [PATCH 05/28] edid-decode: Capitalize fail sentence joevt
                   ` (15 subsequent siblings)
  19 siblings, 0 replies; 21+ messages in thread
From: joevt @ 2021-09-24 23:31 UTC (permalink / raw)
  To: Hans Verkuil; +Cc: linux-media

- if the length is 0 then it cannot get Application Version. Output a fail message.
- cta_hdr10plus may output hex after "Application Version: %u". If the hex is longer than 16 characters, then more lines of hex will be output and they won't align with the first line.
Instead, always start the hex on a new line.

Signed-off-by: Joe van Tunen <joevt@shaw.ca>
---
 parse-cta-block.cpp | 11 ++++++-----
 1 file changed, 6 insertions(+), 5 deletions(-)

diff --git a/parse-cta-block.cpp b/parse-cta-block.cpp
index cee51d7..703f8ca 100644
--- a/parse-cta-block.cpp
+++ b/parse-cta-block.cpp
@@ -1133,11 +1133,12 @@ static void cta_microsoft(const unsigned char *x, unsigned length)
 
 static void cta_hdr10plus(const unsigned char *x, unsigned length)
 {
-	printf("    Application Version: %u", x[0]);
-	if (length > 1)
-		hex_block("  ", x + 1, length - 1);
-	else
-		printf("\n");
+	if (length == 0) {
+		fail("Empty Data Block with length %u.\n", length);
+		return;
+	}
+	printf("    Application Version: %u\n", x[0]);
+	hex_block("    ", x + 1, length - 1);
 }
 
 static void cta_dolby_video(const unsigned char *x, unsigned length)
-- 
2.24.3 (Apple Git-128)


^ permalink raw reply related	[flat|nested] 21+ messages in thread

* [PATCH 05/28] edid-decode: Capitalize fail sentence
  2021-09-24 23:31 [PATCH 00/28] bug fixes, additions, changes joevt
                   ` (3 preceding siblings ...)
  2021-09-24 23:31 ` [PATCH 04/28] edid-decode: check cta_hdr10plus length joevt
@ 2021-09-24 23:31 ` joevt
  2021-09-24 23:31 ` [PATCH 06/28] edid-decode: Replace return with break in switch joevt
                   ` (14 subsequent siblings)
  19 siblings, 0 replies; 21+ messages in thread
From: joevt @ 2021-09-24 23:31 UTC (permalink / raw)
  To: Hans Verkuil; +Cc: linux-media

- Most fail messages are a sentence that starts with a capital letter and ends with a period.
- Remove unnessary break from last switch case.
- Remove extra line.

Signed-off-by: Joe van Tunen <joevt@shaw.ca>
---
 parse-cta-block.cpp | 4 +---
 1 file changed, 1 insertion(+), 3 deletions(-)

diff --git a/parse-cta-block.cpp b/parse-cta-block.cpp
index 703f8ca..f327248 100644
--- a/parse-cta-block.cpp
+++ b/parse-cta-block.cpp
@@ -2055,13 +2055,11 @@ void edid_state::cta_ext_block(const unsigned char *x, unsigned length,
 	case 0x79:
 		if (duplicate)
 			fail("Only one instance of this Data Block is allowed.\n");
-		break;
 	}
 
-
 	// See Table 52 of CTA-861-G for a description of Byte 3
 	if (audio_block && !(cta.byte3 & 0x40))
-		fail("audio information is present, but bit 6 of Byte 3 of the CTA-861 Extension header indicates no Basic Audio support.\n");
+		fail("Audio information is present, but bit 6 of Byte 3 of the CTA-861 Extension header indicates no Basic Audio support.\n");
 
 	if (data_block.length())
 		printf("  %s:\n", data_block.c_str());
-- 
2.24.3 (Apple Git-128)


^ permalink raw reply related	[flat|nested] 21+ messages in thread

* [PATCH 06/28] edid-decode: Replace return with break in switch
  2021-09-24 23:31 [PATCH 00/28] bug fixes, additions, changes joevt
                   ` (4 preceding siblings ...)
  2021-09-24 23:31 ` [PATCH 05/28] edid-decode: Capitalize fail sentence joevt
@ 2021-09-24 23:31 ` joevt
  2021-09-24 23:31 ` [PATCH 07/28] edid-decode: extended tag length check joevt
                   ` (13 subsequent siblings)
  19 siblings, 0 replies; 21+ messages in thread
From: joevt @ 2021-09-24 23:31 UTC (permalink / raw)
  To: Hans Verkuil; +Cc: linux-media

Use break to leave a switch instead of return.
Move code that was after switch to default statement in switch.
This way, we can move switch or have other code after switch.

Signed-off-by: Joe van Tunen <joevt@shaw.ca>
---
 parse-cta-block.cpp | 51 +++++++++++++++++++++++----------------------
 1 file changed, 26 insertions(+), 25 deletions(-)

diff --git a/parse-cta-block.cpp b/parse-cta-block.cpp
index f327248..c561ea4 100644
--- a/parse-cta-block.cpp
+++ b/parse-cta-block.cpp
@@ -2065,12 +2065,12 @@ void edid_state::cta_ext_block(const unsigned char *x, unsigned length,
 		printf("  %s:\n", data_block.c_str());
 
 	switch (x[0]) {
-	case 0x00: cta_vcdb(x + 1, length); return;
+	case 0x00: cta_vcdb(x + 1, length); break;
 	case 0x01:
 		if (length < 3) {
 			data_block = std::string("Vendor-Specific Video Data Block");
 			fail("Invalid length %u < 3.\n", length);
-			return;
+			break;
 		}
 		oui = (x[3] << 16) + (x[2] << 8) + x[1];
 		name = oui_name(oui);
@@ -2086,7 +2086,7 @@ void edid_state::cta_ext_block(const unsigned char *x, unsigned length,
 			data_block.clear();
 			warn("Unknown Extended Vendor-Specific Video Data Block, OUI %s.\n",
 			     ouitohex(oui).c_str());
-			return;
+			break;
 		}
 		data_block = std::string("Vendor-Specific Video Data Block (") + name + ")";
 		if (reverse)
@@ -2098,19 +2098,19 @@ void edid_state::cta_ext_block(const unsigned char *x, unsigned length,
 			cta_dolby_video(x + 4, length - 3);
 		else
 			hex_block("    ", x + 4, length - 3);
-		return;
-	case 0x02: cta_vesa_vdddb(x + 1, length); return;
-	case 0x05: cta_colorimetry_block(x + 1, length); return;
-	case 0x06: cta_hdr_static_metadata_block(x + 1, length); return;
-	case 0x07: cta_hdr_dyn_metadata_block(x + 1, length); return;
-	case 0x0d: cta_vfpdb(x + 1, length); return;
-	case 0x0e: cta_svd(x + 1, length, true); return;
-	case 0x0f: cta_y420cmdb(x + 1, length); return;
+		break;
+	case 0x02: cta_vesa_vdddb(x + 1, length); break;
+	case 0x05: cta_colorimetry_block(x + 1, length); break;
+	case 0x06: cta_hdr_static_metadata_block(x + 1, length); break;
+	case 0x07: cta_hdr_dyn_metadata_block(x + 1, length); break;
+	case 0x0d: cta_vfpdb(x + 1, length); break;
+	case 0x0e: cta_svd(x + 1, length, true); break;
+	case 0x0f: cta_y420cmdb(x + 1, length); break;
 	case 0x11:
 		if (length < 3) {
 			data_block = std::string("Vendor-Specific Audio Data Block");
 			fail("Invalid length %u < 3.\n", length);
-			return;
+			break;
 		}
 		oui = (x[3] << 16) + (x[2] << 8) + x[1];
 		name = oui_name(oui);
@@ -2126,7 +2126,7 @@ void edid_state::cta_ext_block(const unsigned char *x, unsigned length,
 			data_block.clear();
 			warn("Unknown Extended Vendor-Specific Audio Data Block, OUI %s.\n",
 			     ouitohex(oui).c_str());
-			return;
+			break;
 		}
 		data_block = std::string("Vendor-Specific Audio Data Block (") + name + ")";
 		if (reverse)
@@ -2136,20 +2136,20 @@ void edid_state::cta_ext_block(const unsigned char *x, unsigned length,
 			cta_dolby_audio(x + 4, length - 3);
 		else
 			hex_block("    ", x + 4, length - 3);
-		return;
-	case 0x12: cta_hdmi_audio_block(x + 1, length); return;
-	case 0x13: cta_rcdb(x + 1, length); return;
-	case 0x14: cta_sldb(x + 1, length); return;
-	case 0x20: cta_ifdb(x + 1, length); return;
-	case 0x34: cta_displayid_type_7(x + 1, length); return;
-	case 0x35: cta_displayid_type_8(x + 1, length); return;
-	case 0x42: cta_displayid_type_10(x + 1, length); return;
+		break;
+	case 0x12: cta_hdmi_audio_block(x + 1, length); break;
+	case 0x13: cta_rcdb(x + 1, length); break;
+	case 0x14: cta_sldb(x + 1, length); break;
+	case 0x20: cta_ifdb(x + 1, length); break;
+	case 0x34: cta_displayid_type_7(x + 1, length); break;
+	case 0x35: cta_displayid_type_8(x + 1, length); break;
+	case 0x42: cta_displayid_type_10(x + 1, length); break;
 	case 0x78:
 		cta_hf_eeodb(x + 1, length);
 		// This must be the first CTA-861 block
 		if (!cta.first_block)
 			fail("Block starts at a wrong offset.\n");
-		return;
+		break;
 	case 0x79:
 		if (!cta.last_block_was_hdmi_vsdb)
 			fail("HDMI Forum SCDB did not immediately follow the HDMI VSDB.\n");
@@ -2158,16 +2158,17 @@ void edid_state::cta_ext_block(const unsigned char *x, unsigned length,
 		if (length < 2) {
 			data_block = std::string("HDMI Forum SCDB");
 			fail("Invalid length %u < 2.\n", length);
-			return;
+			break;
 		}
 		if (x[1] || x[2])
 			printf("  Non-zero SCDB reserved fields!\n");
 		cta_hf_scdb(x + 3, length - 2);
 		cta.have_hf_scdb = 1;
-		return;
+		break;
+	default:
+		hex_block("    ", x + 1, length);
 	}
 
-	hex_block("    ", x + 1, length);
 }
 
 void edid_state::cta_block(const unsigned char *x, bool duplicate)
-- 
2.24.3 (Apple Git-128)


^ permalink raw reply related	[flat|nested] 21+ messages in thread

* [PATCH 07/28] edid-decode: extended tag length check
  2021-09-24 23:31 [PATCH 00/28] bug fixes, additions, changes joevt
                   ` (5 preceding siblings ...)
  2021-09-24 23:31 ` [PATCH 06/28] edid-decode: Replace return with break in switch joevt
@ 2021-09-24 23:31 ` joevt
  2021-09-24 23:31 ` [PATCH 08/28] edid-decode: Output block type before fail joevt
                   ` (12 subsequent siblings)
  19 siblings, 0 replies; 21+ messages in thread
From: joevt @ 2021-09-24 23:31 UTC (permalink / raw)
  To: Hans Verkuil; +Cc: linux-media

Change:
- Don't read extended tag if length of extended block is zero. Report a fail in that case.

Modifications that don't change behavior but help with the above change or with changes in later commits:
- Differentiate extended tags from normal tags by adding 0x700 to the extended tag byte.
- Increase x after parsing each byte (the tag/length byte and the extended tag byte). Decrease length if there's an extended byte.
- Change cta_ext_block so that x parameter points to byte after the extended tag. Since x points to after extended tag, pass the extended tag as a parameter.
- After reading an OUI, increase x by 3 and decrease length by 3.

Signed-off-by: Joe van Tunen <joevt@shaw.ca>
---
 edid-decode.h       |   2 +-
 parse-cta-block.cpp | 208 ++++++++++++++++++++++++--------------------
 2 files changed, 113 insertions(+), 97 deletions(-)

diff --git a/edid-decode.h b/edid-decode.h
index 612d22a..a41ee6b 100644
--- a/edid-decode.h
+++ b/edid-decode.h
@@ -344,7 +344,7 @@ struct edid_state {
 	void cta_displayid_type_7(const unsigned char *x, unsigned length);
 	void cta_displayid_type_8(const unsigned char *x, unsigned length);
 	void cta_displayid_type_10(const unsigned char *x, unsigned length);
-	void cta_ext_block(const unsigned char *x, unsigned length, bool duplicate);
+	void cta_ext_block(unsigned tag, const unsigned char *x, unsigned length, bool duplicate);
 	void cta_block(const unsigned char *x, bool duplicate);
 	void preparse_cta_block(const unsigned char *x);
 	void parse_cta_block(const unsigned char *x);
diff --git a/parse-cta-block.cpp b/parse-cta-block.cpp
index c561ea4..130fe9e 100644
--- a/parse-cta-block.cpp
+++ b/parse-cta-block.cpp
@@ -1991,7 +1991,7 @@ static void cta_hdmi_audio_block(const unsigned char *x, unsigned length)
 	}
 }
 
-void edid_state::cta_ext_block(const unsigned char *x, unsigned length,
+void edid_state::cta_ext_block(unsigned tag, const unsigned char *x, unsigned length,
 			       bool duplicate)
 {
 	const char *name;
@@ -1999,60 +1999,60 @@ void edid_state::cta_ext_block(const unsigned char *x, unsigned length,
 	bool reverse = false;
 	bool audio_block = false;
 
-	switch (x[0]) {
-	case 0x00: data_block = "Video Capability Data Block"; break;
-	case 0x01: data_block.clear(); break;
-	case 0x02: data_block = "VESA Video Display Device Data Block"; break;
-	case 0x03: data_block = "VESA Video Timing Block Extension"; break;
-	case 0x04: data_block = "Reserved for HDMI Video Data Block"; break;
-	case 0x05: data_block = "Colorimetry Data Block"; break;
-	case 0x06: data_block = "HDR Static Metadata Data Block"; break;
-	case 0x07: data_block = "HDR Dynamic Metadata Data Block"; break;
-
-	case 0x0d: data_block = "Video Format Preference Data Block"; break;
-	case 0x0e: data_block = "YCbCr 4:2:0 Video Data Block"; break;
-	case 0x0f: data_block = "YCbCr 4:2:0 Capability Map Data Block"; break;
-	case 0x10: data_block = "Reserved for CTA-861 Miscellaneous Audio Fields"; break;
-	case 0x11: data_block.clear(); audio_block = true; break;
-	case 0x12: data_block = "HDMI Audio Data Block"; audio_block = true; break;
-	case 0x13: data_block = "Room Configuration Data Block"; audio_block = true; break;
-	case 0x14: data_block = "Speaker Location Data Block"; audio_block = true; break;
-
-	case 0x20: data_block = "InfoFrame Data Block"; break;
-
-	case 0x34: data_block = "DisplayID Type VII Video Timing Data Block"; break;
-	case 0x35: data_block = "DisplayID Type VIII Video Timing Data Block"; break;
-	case 0x42: data_block = "DisplayID Type X Video Timing Data Block"; break;
-
-	case 0x78: data_block = "HDMI Forum EDID Extension Override Data Block"; break;
-	case 0x79: data_block = "HDMI Forum Sink Capability Data Block"; break;
+	switch (tag) {
+	case 0x700: data_block = "Video Capability Data Block"; break;
+	case 0x701: data_block.clear(); break;
+	case 0x702: data_block = "VESA Video Display Device Data Block"; break;
+	case 0x703: data_block = "VESA Video Timing Block Extension"; break;
+	case 0x704: data_block = "Reserved for HDMI Video Data Block"; break;
+	case 0x705: data_block = "Colorimetry Data Block"; break;
+	case 0x706: data_block = "HDR Static Metadata Data Block"; break;
+	case 0x707: data_block = "HDR Dynamic Metadata Data Block"; break;
+
+	case 0x70d: data_block = "Video Format Preference Data Block"; break;
+	case 0x70e: data_block = "YCbCr 4:2:0 Video Data Block"; break;
+	case 0x70f: data_block = "YCbCr 4:2:0 Capability Map Data Block"; break;
+	case 0x710: data_block = "Reserved for CTA-861 Miscellaneous Audio Fields"; break;
+	case 0x711: data_block.clear(); audio_block = true; break;
+	case 0x712: data_block = "HDMI Audio Data Block"; audio_block = true; break;
+	case 0x713: data_block = "Room Configuration Data Block"; audio_block = true; break;
+	case 0x714: data_block = "Speaker Location Data Block"; audio_block = true; break;
+
+	case 0x720: data_block = "InfoFrame Data Block"; break;
+
+	case 0x734: data_block = "DisplayID Type VII Video Timing Data Block"; break;
+	case 0x735: data_block = "DisplayID Type VIII Video Timing Data Block"; break;
+	case 0x742: data_block = "DisplayID Type X Video Timing Data Block"; break;
+
+	case 0x778: data_block = "HDMI Forum EDID Extension Override Data Block"; break;
+	case 0x779: data_block = "HDMI Forum Sink Capability Data Block"; break;
 	default:
-		if (x[0] <= 12)
+		if (tag < 0x70d)
 			printf("  Unknown CTA-861 Video-Related");
-		else if (x[0] <= 31)
+		else if (tag < 0x720)
 			printf("  Unknown CTA-861 Audio-Related");
-		else if (x[0] >= 120 && x[0] <= 127)
+		else if (tag >= 0x778 && tag <= 0x77f)
 			printf("  Unknown CTA-861 HDMI-Related");
 		else
 			printf("  Unknown CTA-861");
-		printf(" Data Block (extended tag 0x%02x, length %u)\n", x[0], length);
-		hex_block("    ", x + 1, length);
+		printf(" Data Block (extended tag 0x%02x)\n", tag & 0xff);
+		hex_block("    ", x, length);
 		data_block.clear();
-		warn("Unknown Extended CTA-861 Data Block 0x%02x.\n", x[0]);
+		warn("Unknown Extended CTA-861 Data Block 0x%02x.\n", tag & 0xff);
 		return;
 	}
 
-	switch (x[0]) {
-	case 0x00:
-	case 0x02:
-	case 0x05:
-	case 0x06:
-	case 0x0d:
-	case 0x0f:
-	case 0x12:
-	case 0x13:
-	case 0x78:
-	case 0x79:
+	switch (tag) {
+	case 0x700:
+	case 0x702:
+	case 0x705:
+	case 0x706:
+	case 0x70d:
+	case 0x70f:
+	case 0x712:
+	case 0x713:
+	case 0x778:
+	case 0x779:
 		if (duplicate)
 			fail("Only one instance of this Data Block is allowed.\n");
 	}
@@ -2064,15 +2064,16 @@ void edid_state::cta_ext_block(const unsigned char *x, unsigned length,
 	if (data_block.length())
 		printf("  %s:\n", data_block.c_str());
 
-	switch (x[0]) {
-	case 0x00: cta_vcdb(x + 1, length); break;
-	case 0x01:
+	switch (tag) {
+	case 0x700: cta_vcdb(x, length); break;
+	case 0x701:
 		if (length < 3) {
 			data_block = std::string("Vendor-Specific Video Data Block");
 			fail("Invalid length %u < 3.\n", length);
 			break;
 		}
-		oui = (x[3] << 16) + (x[2] << 8) + x[1];
+		oui = (x[2] << 16) + (x[1] << 8) + x[0];
+		x += 3; length -=3;
 		name = oui_name(oui);
 		if (!name) {
 			name = oui_name(oui, true);
@@ -2082,7 +2083,7 @@ void edid_state::cta_ext_block(const unsigned char *x, unsigned length,
 		if (!name) {
 			printf("  Vendor-Specific Video Data Block, OUI %s:\n",
 			       ouitohex(oui).c_str());
-			hex_block("    ", x + 4, length - 3);
+			hex_block("    ", x, length);
 			data_block.clear();
 			warn("Unknown Extended Vendor-Specific Video Data Block, OUI %s.\n",
 			     ouitohex(oui).c_str());
@@ -2093,26 +2094,27 @@ void edid_state::cta_ext_block(const unsigned char *x, unsigned length,
 			fail((std::string("OUI ") + ouitohex(oui) + " is in the wrong byte order\n").c_str());
 		printf("  %s, OUI %s:\n", data_block.c_str(), ouitohex(oui).c_str());
 		if (oui == 0x90848b)
-			cta_hdr10plus(x + 4, length - 3);
+			cta_hdr10plus(x, length);
 		else if (oui == 0x00d046)
-			cta_dolby_video(x + 4, length - 3);
+			cta_dolby_video(x, length);
 		else
-			hex_block("    ", x + 4, length - 3);
+			hex_block("    ", x, length);
 		break;
-	case 0x02: cta_vesa_vdddb(x + 1, length); break;
-	case 0x05: cta_colorimetry_block(x + 1, length); break;
-	case 0x06: cta_hdr_static_metadata_block(x + 1, length); break;
-	case 0x07: cta_hdr_dyn_metadata_block(x + 1, length); break;
-	case 0x0d: cta_vfpdb(x + 1, length); break;
-	case 0x0e: cta_svd(x + 1, length, true); break;
-	case 0x0f: cta_y420cmdb(x + 1, length); break;
-	case 0x11:
+	case 0x702: cta_vesa_vdddb(x, length); break;
+	case 0x705: cta_colorimetry_block(x, length); break;
+	case 0x706: cta_hdr_static_metadata_block(x, length); break;
+	case 0x707: cta_hdr_dyn_metadata_block(x, length); break;
+	case 0x70d: cta_vfpdb(x, length); break;
+	case 0x70e: cta_svd(x, length, true); break;
+	case 0x70f: cta_y420cmdb(x, length); break;
+	case 0x711:
 		if (length < 3) {
 			data_block = std::string("Vendor-Specific Audio Data Block");
 			fail("Invalid length %u < 3.\n", length);
 			break;
 		}
-		oui = (x[3] << 16) + (x[2] << 8) + x[1];
+		oui = (x[2] << 16) + (x[1] << 8) + x[0];
+		x += 3; length -=3;
 		name = oui_name(oui);
 		if (!name) {
 			name = oui_name(oui, true);
@@ -2122,7 +2124,7 @@ void edid_state::cta_ext_block(const unsigned char *x, unsigned length,
 		if (!name) {
 			printf("  Vendor-Specific Audio Data Block, OUI %s:\n",
 			       ouitohex(oui).c_str());
-			hex_block("    ", x + 4, length - 3);
+			hex_block("    ", x, length);
 			data_block.clear();
 			warn("Unknown Extended Vendor-Specific Audio Data Block, OUI %s.\n",
 			     ouitohex(oui).c_str());
@@ -2133,24 +2135,24 @@ void edid_state::cta_ext_block(const unsigned char *x, unsigned length,
 			fail((std::string("OUI ") + ouitohex(oui) + " is in the wrong byte order\n").c_str());
 		printf("  %s, OUI %s:\n", data_block.c_str(), ouitohex(oui).c_str());
 		if (oui == 0x00d046)
-			cta_dolby_audio(x + 4, length - 3);
+			cta_dolby_audio(x, length);
 		else
-			hex_block("    ", x + 4, length - 3);
+			hex_block("    ", x, length);
 		break;
-	case 0x12: cta_hdmi_audio_block(x + 1, length); break;
-	case 0x13: cta_rcdb(x + 1, length); break;
-	case 0x14: cta_sldb(x + 1, length); break;
-	case 0x20: cta_ifdb(x + 1, length); break;
-	case 0x34: cta_displayid_type_7(x + 1, length); break;
-	case 0x35: cta_displayid_type_8(x + 1, length); break;
-	case 0x42: cta_displayid_type_10(x + 1, length); break;
-	case 0x78:
-		cta_hf_eeodb(x + 1, length);
+	case 0x712: cta_hdmi_audio_block(x, length); break;
+	case 0x713: cta_rcdb(x, length); break;
+	case 0x714: cta_sldb(x, length); break;
+	case 0x720: cta_ifdb(x, length); break;
+	case 0x734: cta_displayid_type_7(x, length); break;
+	case 0x735: cta_displayid_type_8(x, length); break;
+	case 0x742: cta_displayid_type_10(x, length); break;
+	case 0x778:
+		cta_hf_eeodb(x, length);
 		// This must be the first CTA-861 block
 		if (!cta.first_block)
 			fail("Block starts at a wrong offset.\n");
 		break;
-	case 0x79:
+	case 0x779:
 		if (!cta.last_block_was_hdmi_vsdb)
 			fail("HDMI Forum SCDB did not immediately follow the HDMI VSDB.\n");
 		if (cta.have_hf_scdb || cta.have_hf_vsdb)
@@ -2160,13 +2162,13 @@ void edid_state::cta_ext_block(const unsigned char *x, unsigned length,
 			fail("Invalid length %u < 2.\n", length);
 			break;
 		}
-		if (x[1] || x[2])
+		if (x[0] || x[1])
 			printf("  Non-zero SCDB reserved fields!\n");
-		cta_hf_scdb(x + 3, length - 2);
+		cta_hf_scdb(x + 2, length - 2);
 		cta.have_hf_scdb = 1;
 		break;
 	default:
-		hex_block("    ", x + 1, length);
+		hex_block("    ", x, length);
 	}
 
 }
@@ -2174,25 +2176,36 @@ void edid_state::cta_ext_block(const unsigned char *x, unsigned length,
 void edid_state::cta_block(const unsigned char *x, bool duplicate)
 {
 	unsigned length = x[0] & 0x1f;
+	unsigned tag=(x[0] & 0xe0) >> 5;
+	unsigned extended = (tag == 0x07) ? 1 : 0;
+	x++;
+	if (extended && length) {
+		tag <<= 8;
+		tag |= x[0];
+		length--;
+		x++;
+	}
+
 	const char *name;
 	unsigned oui;
 	bool reverse = false;
 	bool audio_block = false;
 
-	switch ((x[0] & 0xe0) >> 5) {
+	switch (tag) {
 	case 0x01:
 		data_block = "Audio Data Block";
 		printf("  %s:\n", data_block.c_str());
-		cta_audio_block(x + 1, length);
+		cta_audio_block(x, length);
 		audio_block = true;
 		break;
 	case 0x02:
 		data_block = "Video Data Block";
 		printf("  %s:\n", data_block.c_str());
-		cta_svd(x + 1, length, false);
+		cta_svd(x, length, false);
 		break;
 	case 0x03:
-		oui = (x[3] << 16) + (x[2] << 8) + x[1];
+		oui = (x[2] << 16) + (x[1] << 8) + x[0];
+		x += 3; length -=3;
 		name = oui_name(oui);
 		if (!name) {
 			name = oui_name(oui, true);
@@ -2201,7 +2214,7 @@ void edid_state::cta_block(const unsigned char *x, bool duplicate)
 		}
 		if (!name) {
 			printf("  Vendor-Specific Data Block, OUI %s:\n", ouitohex(oui).c_str());
-			hex_block("    ", x + 4, length - 3);
+			hex_block("    ", x, length);
 			data_block.clear();
 			warn("Unknown Vendor-Specific Data Block, OUI %s.\n",
 			     ouitohex(oui).c_str());
@@ -2212,7 +2225,7 @@ void edid_state::cta_block(const unsigned char *x, bool duplicate)
 			fail((std::string("OUI ") + ouitohex(oui) + " is in the wrong byte order\n").c_str());
 		printf("  %s, OUI %s:\n", data_block.c_str(), ouitohex(oui).c_str());
 		if (oui == 0x000c03) {
-			cta_hdmi_block(x + 4, length - 3);
+			cta_hdmi_block(x, length);
 			cta.last_block_was_hdmi_vsdb = 1;
 			cta.first_block = 0;
 			// The HDMI OUI is present, so this EDID represents an HDMI
@@ -2228,24 +2241,24 @@ void edid_state::cta_block(const unsigned char *x, bool duplicate)
 				fail("HDMI Forum VSDB did not immediately follow the HDMI VSDB.\n");
 			if (cta.have_hf_scdb || cta.have_hf_vsdb)
 				fail("Duplicate HDMI Forum VSDB/SCDB.\n");
-			cta_hf_scdb(x + 4, length - 3);
+			cta_hf_scdb(x, length);
 			cta.have_hf_vsdb = 1;
 			break;
 		}
 		if (oui == 0x00001a) {
-			cta_amd(x + 4, length - 3);
+			cta_amd(x, length);
 			break;
 		}
 		if (oui == 0xca125c && length == 0x15) {
-			cta_microsoft(x + 4, length - 3);
+			cta_microsoft(x, length);
 			break;
 		}
-		hex_block("    ", x + 4, length - 3);
+		hex_block("    ", x, length);
 		break;
 	case 0x04:
 		data_block = "Speaker Allocation Data Block";
 		printf("  %s:\n", data_block.c_str());
-		cta_sadb(x + 1, length);
+		cta_sadb(x, length);
 		audio_block = true;
 		if (duplicate)
 			fail("Only one instance of this Data Block is allowed.\n");
@@ -2253,19 +2266,22 @@ void edid_state::cta_block(const unsigned char *x, bool duplicate)
 	case 0x05:
 		data_block = "VESA Display Transfer Characteristics Data Block";
 		printf("  %s:\n", data_block.c_str());
-		cta_vesa_dtcdb(x + 1, length);
+		cta_vesa_dtcdb(x, length);
 		if (duplicate)
 			fail("Only one instance of this Data Block is allowed.\n");
 		break;
 	case 0x07:
-		cta_ext_block(x + 1, length - 1, duplicate);
+		data_block = "Unknown CTA-861 Data Block (extended tag truncated)";
+		printf("  %s:\n", data_block.c_str());
+		fail("Extended tag cannot have zero length.\n");
 		break;
 	default: {
-		unsigned tag = (*x & 0xe0) >> 5;
-		unsigned length = *x & 0x1f;
-
-		printf("  Unknown CTA-861 tag 0x%02x, length %u\n", tag, length);
-		hex_block("    ", x + 1, length);
+		if (extended) {
+			cta_ext_block(tag, x, length, duplicate);
+			break;
+		}
+		printf("  Unknown CTA-861 tag 0x%02x\n", tag);
+		hex_block("    ", x, length);
 		data_block.clear();
 		warn("Unknown CTA-861 Data Block %u.\n", tag);
 		break;
-- 
2.24.3 (Apple Git-128)


^ permalink raw reply related	[flat|nested] 21+ messages in thread

* [PATCH 08/28] edid-decode: Output block type before fail
  2021-09-24 23:31 [PATCH 00/28] bug fixes, additions, changes joevt
                   ` (6 preceding siblings ...)
  2021-09-24 23:31 ` [PATCH 07/28] edid-decode: extended tag length check joevt
@ 2021-09-24 23:31 ` joevt
  2021-09-24 23:31 ` [PATCH 09/28] edid-decode: update Microsoft expected length joevt
                   ` (11 subsequent siblings)
  19 siblings, 0 replies; 21+ messages in thread
From: joevt @ 2021-09-24 23:31 UTC (permalink / raw)
  To: Hans Verkuil; +Cc: linux-media

For extended tags, block type should be output before fail messages (duplicate failure, or missing audio failure).
For normal tags 0x04 and 0x05, fail message should appear after block type instead of block data to be consistent (and also to indicate that the failure is because of the block type and not the contents of the block).

Signed-off-by: Joe van Tunen <joevt@shaw.ca>
---
 parse-cta-block.cpp | 12 ++++++------
 1 file changed, 6 insertions(+), 6 deletions(-)

diff --git a/parse-cta-block.cpp b/parse-cta-block.cpp
index 130fe9e..d6c797d 100644
--- a/parse-cta-block.cpp
+++ b/parse-cta-block.cpp
@@ -2042,6 +2042,9 @@ void edid_state::cta_ext_block(unsigned tag, const unsigned char *x, unsigned le
 		return;
 	}
 
+	if (data_block.length())
+		printf("  %s:\n", data_block.c_str());
+
 	switch (tag) {
 	case 0x700:
 	case 0x702:
@@ -2061,9 +2064,6 @@ void edid_state::cta_ext_block(unsigned tag, const unsigned char *x, unsigned le
 	if (audio_block && !(cta.byte3 & 0x40))
 		fail("Audio information is present, but bit 6 of Byte 3 of the CTA-861 Extension header indicates no Basic Audio support.\n");
 
-	if (data_block.length())
-		printf("  %s:\n", data_block.c_str());
-
 	switch (tag) {
 	case 0x700: cta_vcdb(x, length); break;
 	case 0x701:
@@ -2258,17 +2258,17 @@ void edid_state::cta_block(const unsigned char *x, bool duplicate)
 	case 0x04:
 		data_block = "Speaker Allocation Data Block";
 		printf("  %s:\n", data_block.c_str());
-		cta_sadb(x, length);
-		audio_block = true;
 		if (duplicate)
 			fail("Only one instance of this Data Block is allowed.\n");
+		cta_sadb(x, length);
+		audio_block = true;
 		break;
 	case 0x05:
 		data_block = "VESA Display Transfer Characteristics Data Block";
 		printf("  %s:\n", data_block.c_str());
-		cta_vesa_dtcdb(x, length);
 		if (duplicate)
 			fail("Only one instance of this Data Block is allowed.\n");
+		cta_vesa_dtcdb(x, length);
 		break;
 	case 0x07:
 		data_block = "Unknown CTA-861 Data Block (extended tag truncated)";
-- 
2.24.3 (Apple Git-128)


^ permalink raw reply related	[flat|nested] 21+ messages in thread

* [PATCH 09/28] edid-decode: update Microsoft expected length
  2021-09-24 23:31 [PATCH 00/28] bug fixes, additions, changes joevt
                   ` (7 preceding siblings ...)
  2021-09-24 23:31 ` [PATCH 08/28] edid-decode: Output block type before fail joevt
@ 2021-09-24 23:31 ` joevt
  2021-09-24 23:31 ` [PATCH 10/28] edid-decode: Capitalize fail sentence joevt
                   ` (10 subsequent siblings)
  19 siblings, 0 replies; 21+ messages in thread
From: joevt @ 2021-09-24 23:31 UTC (permalink / raw)
  To: Hans Verkuil; +Cc: linux-media

Since we excluded the size of the OUI from the length in a previous commit, we need to decrease the expected length accordingly.
See example DELA07B/5F1B08ADB0A0, LENB800/61B4B713B745

Really, length checks should probably be done in the parse function. If length is greater than expected then parse up to the expected length and output the rest as hex with a warning. If length is less than expected then parse up to the length and warn that some expected bytes are missing.

Signed-off-by: Joe van Tunen <joevt@shaw.ca>
---
 parse-cta-block.cpp | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/parse-cta-block.cpp b/parse-cta-block.cpp
index d6c797d..ea55c99 100644
--- a/parse-cta-block.cpp
+++ b/parse-cta-block.cpp
@@ -2249,7 +2249,7 @@ void edid_state::cta_block(const unsigned char *x, bool duplicate)
 			cta_amd(x, length);
 			break;
 		}
-		if (oui == 0xca125c && length == 0x15) {
+		if (oui == 0xca125c && length == 0x12) {
 			cta_microsoft(x, length);
 			break;
 		}
-- 
2.24.3 (Apple Git-128)


^ permalink raw reply related	[flat|nested] 21+ messages in thread

* [PATCH 10/28] edid-decode: Capitalize fail sentence
  2021-09-24 23:31 [PATCH 00/28] bug fixes, additions, changes joevt
                   ` (8 preceding siblings ...)
  2021-09-24 23:31 ` [PATCH 09/28] edid-decode: update Microsoft expected length joevt
@ 2021-09-24 23:31 ` joevt
  2021-09-24 23:31 ` [PATCH 11/28] edid-decode: make all OUI handlers the same joevt
                   ` (9 subsequent siblings)
  19 siblings, 0 replies; 21+ messages in thread
From: joevt @ 2021-09-24 23:31 UTC (permalink / raw)
  To: Hans Verkuil; +Cc: linux-media

Most fail messages are a sentence that starts with a capital letter and ends with a period.

Signed-off-by: Joe van Tunen <joevt@shaw.ca>
---
 parse-cta-block.cpp | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/parse-cta-block.cpp b/parse-cta-block.cpp
index ea55c99..975381f 100644
--- a/parse-cta-block.cpp
+++ b/parse-cta-block.cpp
@@ -2290,7 +2290,7 @@ void edid_state::cta_block(const unsigned char *x, bool duplicate)
 
 	// See Table 52 of CTA-861-G for a description of Byte 3
 	if (audio_block && !(cta.byte3 & 0x40))
-		fail("audio information is present, but bit 6 of Byte 3 of the CTA-861 Extension header indicates no Basic Audio support.\n");
+		fail("Audio information is present, but bit 6 of Byte 3 of the CTA-861 Extension header indicates no Basic Audio support.\n");
 	cta.first_block = 0;
 	cta.last_block_was_hdmi_vsdb = 0;
 }
-- 
2.24.3 (Apple Git-128)


^ permalink raw reply related	[flat|nested] 21+ messages in thread

* [PATCH 11/28] edid-decode: make all OUI handlers the same
  2021-09-24 23:31 [PATCH 00/28] bug fixes, additions, changes joevt
                   ` (9 preceding siblings ...)
  2021-09-24 23:31 ` [PATCH 10/28] edid-decode: Capitalize fail sentence joevt
@ 2021-09-24 23:31 ` joevt
  2021-09-24 23:31 ` [PATCH 12/28] edid-decode: move OUI parsing to separate function joevt
                   ` (8 subsequent siblings)
  19 siblings, 0 replies; 21+ messages in thread
From: joevt @ 2021-09-24 23:31 UTC (permalink / raw)
  To: Hans Verkuil; +Cc: linux-media

Because they are the same but with different block names.

For Vendor-Specific Data Block there are a couple fixes:
1) If the length is not enough to contain an OUI, then a fail is output. I have a corrupted EDID that would cause 20000+ lines of hex to be output without this check.
2) The return statement for VSDB with unknown OUI is changed to a break statement. The code after the switch statement will be executed which causes the block to be considered as a first block or as not a hdmi vsdb.

Signed-off-by: Joe van Tunen <joevt@shaw.ca>
---
 parse-cta-block.cpp | 39 ++++++++++++++++++++++-----------------
 1 file changed, 22 insertions(+), 17 deletions(-)

diff --git a/parse-cta-block.cpp b/parse-cta-block.cpp
index 975381f..2c83a35 100644
--- a/parse-cta-block.cpp
+++ b/parse-cta-block.cpp
@@ -1994,6 +1994,7 @@ static void cta_hdmi_audio_block(const unsigned char *x, unsigned length)
 void edid_state::cta_ext_block(unsigned tag, const unsigned char *x, unsigned length,
 			       bool duplicate)
 {
+	const char *block_name;
 	const char *name;
 	unsigned oui;
 	bool reverse = false;
@@ -2067,8 +2068,9 @@ void edid_state::cta_ext_block(unsigned tag, const unsigned char *x, unsigned le
 	switch (tag) {
 	case 0x700: cta_vcdb(x, length); break;
 	case 0x701:
+		block_name = "Vendor-Specific Video Data Block";
 		if (length < 3) {
-			data_block = std::string("Vendor-Specific Video Data Block");
+			data_block = std::string(block_name);
 			fail("Invalid length %u < 3.\n", length);
 			break;
 		}
@@ -2081,15 +2083,13 @@ void edid_state::cta_ext_block(unsigned tag, const unsigned char *x, unsigned le
 				reverse = true;
 		}
 		if (!name) {
-			printf("  Vendor-Specific Video Data Block, OUI %s:\n",
-			       ouitohex(oui).c_str());
+			printf("  %s, OUI %s:\n", block_name, ouitohex(oui).c_str());
 			hex_block("    ", x, length);
 			data_block.clear();
-			warn("Unknown Extended Vendor-Specific Video Data Block, OUI %s.\n",
-			     ouitohex(oui).c_str());
+			warn("Unknown %s, OUI %s.\n", block_name, ouitohex(oui).c_str());
 			break;
 		}
-		data_block = std::string("Vendor-Specific Video Data Block (") + name + ")";
+		data_block = std::string(block_name) + " (" + name + ")";
 		if (reverse)
 			fail((std::string("OUI ") + ouitohex(oui) + " is in the wrong byte order\n").c_str());
 		printf("  %s, OUI %s:\n", data_block.c_str(), ouitohex(oui).c_str());
@@ -2108,8 +2108,9 @@ void edid_state::cta_ext_block(unsigned tag, const unsigned char *x, unsigned le
 	case 0x70e: cta_svd(x, length, true); break;
 	case 0x70f: cta_y420cmdb(x, length); break;
 	case 0x711:
+		block_name = "Vendor-Specific Audio Data Block";
 		if (length < 3) {
-			data_block = std::string("Vendor-Specific Audio Data Block");
+			data_block = std::string(block_name);
 			fail("Invalid length %u < 3.\n", length);
 			break;
 		}
@@ -2122,15 +2123,13 @@ void edid_state::cta_ext_block(unsigned tag, const unsigned char *x, unsigned le
 				reverse = true;
 		}
 		if (!name) {
-			printf("  Vendor-Specific Audio Data Block, OUI %s:\n",
-			       ouitohex(oui).c_str());
+			printf("  %s, OUI %s:\n", block_name, ouitohex(oui).c_str());
 			hex_block("    ", x, length);
 			data_block.clear();
-			warn("Unknown Extended Vendor-Specific Audio Data Block, OUI %s.\n",
-			     ouitohex(oui).c_str());
+			warn("Unknown %s, OUI %s.\n", block_name, ouitohex(oui).c_str());
 			break;
 		}
-		data_block = std::string("Vendor-Specific Audio Data Block (") + name + ")";
+		data_block = std::string(block_name) + " (" + name + ")";
 		if (reverse)
 			fail((std::string("OUI ") + ouitohex(oui) + " is in the wrong byte order\n").c_str());
 		printf("  %s, OUI %s:\n", data_block.c_str(), ouitohex(oui).c_str());
@@ -2186,6 +2185,7 @@ void edid_state::cta_block(const unsigned char *x, bool duplicate)
 		x++;
 	}
 
+	const char *block_name;
 	const char *name;
 	unsigned oui;
 	bool reverse = false;
@@ -2204,6 +2204,12 @@ void edid_state::cta_block(const unsigned char *x, bool duplicate)
 		cta_svd(x, length, false);
 		break;
 	case 0x03:
+		block_name = "Vendor-Specific Data Block";
+		if (length < 3) {
+			data_block = std::string(block_name);
+			fail("Invalid length %u < 3.\n", length);
+			break;
+		}
 		oui = (x[2] << 16) + (x[1] << 8) + x[0];
 		x += 3; length -=3;
 		name = oui_name(oui);
@@ -2213,14 +2219,13 @@ void edid_state::cta_block(const unsigned char *x, bool duplicate)
 				reverse = true;
 		}
 		if (!name) {
-			printf("  Vendor-Specific Data Block, OUI %s:\n", ouitohex(oui).c_str());
+			printf("  %s, OUI %s:\n", block_name, ouitohex(oui).c_str());
 			hex_block("    ", x, length);
 			data_block.clear();
-			warn("Unknown Vendor-Specific Data Block, OUI %s.\n",
-			     ouitohex(oui).c_str());
-			return;
+			warn("Unknown %s, OUI %s.\n", block_name, ouitohex(oui).c_str());
+			break;
 		}
-		data_block = std::string("Vendor-Specific Data Block (") + name + ")";
+		data_block = std::string(block_name) + " (" + name + ")";
 		if (reverse)
 			fail((std::string("OUI ") + ouitohex(oui) + " is in the wrong byte order\n").c_str());
 		printf("  %s, OUI %s:\n", data_block.c_str(), ouitohex(oui).c_str());
-- 
2.24.3 (Apple Git-128)


^ permalink raw reply related	[flat|nested] 21+ messages in thread

* [PATCH 12/28] edid-decode: move OUI parsing to separate function
  2021-09-24 23:31 [PATCH 00/28] bug fixes, additions, changes joevt
                   ` (10 preceding siblings ...)
  2021-09-24 23:31 ` [PATCH 11/28] edid-decode: make all OUI handlers the same joevt
@ 2021-09-24 23:31 ` joevt
  2021-09-24 23:31 ` [PATCH 13/28] edid-decode: move unknown block warning joevt
                   ` (7 subsequent siblings)
  19 siblings, 0 replies; 21+ messages in thread
From: joevt @ 2021-09-24 23:31 UTC (permalink / raw)
  To: Hans Verkuil; +Cc: linux-media

Since all three occurrences of OUI parsing are the same in parse-cta-block.cpp, we can move them to a separate function in edid-decode.cpp (because we may want to use the function for non-CTA parsing as well).

data_block_oui contains identical code except for the following:
1) The warning for unknown OUI name is output after the block name instead of after the block contents.

Other changes that don't affect output:
- oui is set to 0 if the OUI is unknown so that it can't lead to executing any known OUI code by the caller.
- A macro is used to call data_block_oui. It updates x and length appropriately for the caller.

Signed-off-by: Joe van Tunen <joevt@shaw.ca>
---
 edid-decode.cpp     | 34 +++++++++++++++++
 edid-decode.h       |  2 +
 parse-cta-block.cpp | 91 +++++----------------------------------------
 3 files changed, 46 insertions(+), 81 deletions(-)

diff --git a/edid-decode.cpp b/edid-decode.cpp
index d77646d..ec903f9 100644
--- a/edid-decode.cpp
+++ b/edid-decode.cpp
@@ -679,6 +679,40 @@ const char *oui_name(unsigned oui, bool reverse)
 	}
 }
 
+void edid_state::data_block_oui(const char *block_name, const unsigned char *x, unsigned length, unsigned *ouinum)
+{
+	const char *name;
+	unsigned oui = 0;
+	bool reverse = false;
+
+	if (length < 3) {
+		data_block = std::string(block_name);
+		fail("Invalid length %u < 3.\n", length);
+	}
+	else {
+		oui = (x[2] << 16) + (x[1] << 8) + x[0];
+		x += 3; length -=3;
+		name = oui_name(oui);
+		if (!name) {
+			name = oui_name(oui, true);
+			if (name)
+				reverse = true;
+		}
+		if (!name) {
+			printf("  %s, OUI %s:\n", block_name, ouitohex(oui).c_str());
+			data_block.clear();
+			warn("Unknown %s, OUI %s.\n", block_name, ouitohex(oui).c_str());
+		}
+		else {
+			data_block = std::string(block_name) + " (" + name + ")";
+			if (reverse)
+				fail((std::string("OUI ") + ouitohex(oui) + " is in the wrong byte order\n").c_str());
+			printf("  %s, OUI %s:\n", data_block.c_str(), ouitohex(oui).c_str());
+		}
+	}
+	if (ouinum) *ouinum = oui;
+}
+
 std::string ouitohex(unsigned oui)
 {
 	char buf[32];
diff --git a/edid-decode.h b/edid-decode.h
index a41ee6b..ca130c5 100644
--- a/edid-decode.h
+++ b/edid-decode.h
@@ -331,6 +331,8 @@ struct edid_state {
 	void list_dmts();
 	void list_established_timings();
 
+	void data_block_oui(const char *block_name, const unsigned char *x, unsigned length, unsigned *ouinum);
+
 	void print_vic_index(const char *prefix, unsigned idx, const char *suffix, bool ycbcr420 = false);
 	void hdmi_latency(unsigned char vid_lat, unsigned char aud_lat, bool is_ilaced);
 	void cta_vcdb(const unsigned char *x, unsigned length);
diff --git a/parse-cta-block.cpp b/parse-cta-block.cpp
index 2c83a35..cd7650d 100644
--- a/parse-cta-block.cpp
+++ b/parse-cta-block.cpp
@@ -1991,13 +1991,17 @@ static void cta_hdmi_audio_block(const unsigned char *x, unsigned length)
 	}
 }
 
+#define data_block_o(n) \
+	do { \
+		data_block_oui(n, x, length, &oui); \
+		x += (length < 3) ? length : 3; \
+		length -= (length < 3) ? length : 3; \
+	} while(0)
+
 void edid_state::cta_ext_block(unsigned tag, const unsigned char *x, unsigned length,
 			       bool duplicate)
 {
-	const char *block_name;
-	const char *name;
 	unsigned oui;
-	bool reverse = false;
 	bool audio_block = false;
 
 	switch (tag) {
@@ -2068,31 +2072,7 @@ void edid_state::cta_ext_block(unsigned tag, const unsigned char *x, unsigned le
 	switch (tag) {
 	case 0x700: cta_vcdb(x, length); break;
 	case 0x701:
-		block_name = "Vendor-Specific Video Data Block";
-		if (length < 3) {
-			data_block = std::string(block_name);
-			fail("Invalid length %u < 3.\n", length);
-			break;
-		}
-		oui = (x[2] << 16) + (x[1] << 8) + x[0];
-		x += 3; length -=3;
-		name = oui_name(oui);
-		if (!name) {
-			name = oui_name(oui, true);
-			if (name)
-				reverse = true;
-		}
-		if (!name) {
-			printf("  %s, OUI %s:\n", block_name, ouitohex(oui).c_str());
-			hex_block("    ", x, length);
-			data_block.clear();
-			warn("Unknown %s, OUI %s.\n", block_name, ouitohex(oui).c_str());
-			break;
-		}
-		data_block = std::string(block_name) + " (" + name + ")";
-		if (reverse)
-			fail((std::string("OUI ") + ouitohex(oui) + " is in the wrong byte order\n").c_str());
-		printf("  %s, OUI %s:\n", data_block.c_str(), ouitohex(oui).c_str());
+		data_block_o("Vendor-Specific Video Data Block");
 		if (oui == 0x90848b)
 			cta_hdr10plus(x, length);
 		else if (oui == 0x00d046)
@@ -2108,31 +2088,7 @@ void edid_state::cta_ext_block(unsigned tag, const unsigned char *x, unsigned le
 	case 0x70e: cta_svd(x, length, true); break;
 	case 0x70f: cta_y420cmdb(x, length); break;
 	case 0x711:
-		block_name = "Vendor-Specific Audio Data Block";
-		if (length < 3) {
-			data_block = std::string(block_name);
-			fail("Invalid length %u < 3.\n", length);
-			break;
-		}
-		oui = (x[2] << 16) + (x[1] << 8) + x[0];
-		x += 3; length -=3;
-		name = oui_name(oui);
-		if (!name) {
-			name = oui_name(oui, true);
-			if (name)
-				reverse = true;
-		}
-		if (!name) {
-			printf("  %s, OUI %s:\n", block_name, ouitohex(oui).c_str());
-			hex_block("    ", x, length);
-			data_block.clear();
-			warn("Unknown %s, OUI %s.\n", block_name, ouitohex(oui).c_str());
-			break;
-		}
-		data_block = std::string(block_name) + " (" + name + ")";
-		if (reverse)
-			fail((std::string("OUI ") + ouitohex(oui) + " is in the wrong byte order\n").c_str());
-		printf("  %s, OUI %s:\n", data_block.c_str(), ouitohex(oui).c_str());
+		data_block_o("Vendor-Specific Audio Data Block");
 		if (oui == 0x00d046)
 			cta_dolby_audio(x, length);
 		else
@@ -2185,10 +2141,7 @@ void edid_state::cta_block(const unsigned char *x, bool duplicate)
 		x++;
 	}
 
-	const char *block_name;
-	const char *name;
 	unsigned oui;
-	bool reverse = false;
 	bool audio_block = false;
 
 	switch (tag) {
@@ -2204,31 +2157,7 @@ void edid_state::cta_block(const unsigned char *x, bool duplicate)
 		cta_svd(x, length, false);
 		break;
 	case 0x03:
-		block_name = "Vendor-Specific Data Block";
-		if (length < 3) {
-			data_block = std::string(block_name);
-			fail("Invalid length %u < 3.\n", length);
-			break;
-		}
-		oui = (x[2] << 16) + (x[1] << 8) + x[0];
-		x += 3; length -=3;
-		name = oui_name(oui);
-		if (!name) {
-			name = oui_name(oui, true);
-			if (name)
-				reverse = true;
-		}
-		if (!name) {
-			printf("  %s, OUI %s:\n", block_name, ouitohex(oui).c_str());
-			hex_block("    ", x, length);
-			data_block.clear();
-			warn("Unknown %s, OUI %s.\n", block_name, ouitohex(oui).c_str());
-			break;
-		}
-		data_block = std::string(block_name) + " (" + name + ")";
-		if (reverse)
-			fail((std::string("OUI ") + ouitohex(oui) + " is in the wrong byte order\n").c_str());
-		printf("  %s, OUI %s:\n", data_block.c_str(), ouitohex(oui).c_str());
+		data_block_o("Vendor-Specific Data Block");
 		if (oui == 0x000c03) {
 			cta_hdmi_block(x, length);
 			cta.last_block_was_hdmi_vsdb = 1;
-- 
2.24.3 (Apple Git-128)


^ permalink raw reply related	[flat|nested] 21+ messages in thread

* [PATCH 13/28] edid-decode: move unknown block warning
  2021-09-24 23:31 [PATCH 00/28] bug fixes, additions, changes joevt
                   ` (11 preceding siblings ...)
  2021-09-24 23:31 ` [PATCH 12/28] edid-decode: move OUI parsing to separate function joevt
@ 2021-09-24 23:31 ` joevt
  2021-09-24 23:31 ` [PATCH 14/28] edid-decode: remove cta_ext_block joevt
                   ` (6 subsequent siblings)
  19 siblings, 0 replies; 21+ messages in thread
From: joevt @ 2021-09-24 23:31 UTC (permalink / raw)
  To: Hans Verkuil; +Cc: linux-media

Also, make cta_block like cta_ext_block

First, fix the first switch statement in cta_ext_block. The first switch statement sets or clears data_block (the name of the block which is used in the Warnings and Failures section of the output).
Remove hex_block because it will be done by the third switch statement that handles outputting the contents of each block.
The "Unknown Extended CTA-861 Data Block 0x%02x.\n" warning now appears after the block name instead of after the block contents (because it's not the contents that caused the error).

Then, in cta_block:
1) Create a first switch statement like that of cta_ext_block (described above).
The "Unknown CTA-861 Data Block %u.\n" warning now appears after the block name instead of after the block contents (because it's not the contents that caused the error).
2) Create a second switch statement like that of cta_ext_block. It handles checking for duplicate blocks.
3) After checking for duplicates, check cta_byte3 / audio_block discrepancy, exactly like cta_ext_block does. These lines come from after the original switch statement of cta_block.
4) The original switch statement of cta_block has lines that are moved to the new first and second switch statements.

Signed-off-by: Joe van Tunen <joevt@shaw.ca>
---
 parse-cta-block.cpp | 82 +++++++++++++++++++++------------------------
 1 file changed, 38 insertions(+), 44 deletions(-)

diff --git a/parse-cta-block.cpp b/parse-cta-block.cpp
index cd7650d..be76903 100644
--- a/parse-cta-block.cpp
+++ b/parse-cta-block.cpp
@@ -2032,6 +2032,7 @@ void edid_state::cta_ext_block(unsigned tag, const unsigned char *x, unsigned le
 	case 0x778: data_block = "HDMI Forum EDID Extension Override Data Block"; break;
 	case 0x779: data_block = "HDMI Forum Sink Capability Data Block"; break;
 	default:
+		data_block.clear();
 		if (tag < 0x70d)
 			printf("  Unknown CTA-861 Video-Related");
 		else if (tag < 0x720)
@@ -2041,10 +2042,7 @@ void edid_state::cta_ext_block(unsigned tag, const unsigned char *x, unsigned le
 		else
 			printf("  Unknown CTA-861");
 		printf(" Data Block (extended tag 0x%02x)\n", tag & 0xff);
-		hex_block("    ", x, length);
-		data_block.clear();
 		warn("Unknown Extended CTA-861 Data Block 0x%02x.\n", tag & 0xff);
-		return;
 	}
 
 	if (data_block.length())
@@ -2125,7 +2123,6 @@ void edid_state::cta_ext_block(unsigned tag, const unsigned char *x, unsigned le
 	default:
 		hex_block("    ", x, length);
 	}
-
 }
 
 void edid_state::cta_block(const unsigned char *x, bool duplicate)
@@ -2145,17 +2142,37 @@ void edid_state::cta_block(const unsigned char *x, bool duplicate)
 	bool audio_block = false;
 
 	switch (tag) {
-	case 0x01:
-		data_block = "Audio Data Block";
-		printf("  %s:\n", data_block.c_str());
-		cta_audio_block(x, length);
-		audio_block = true;
-		break;
-	case 0x02:
-		data_block = "Video Data Block";
+	case 0x01: data_block = "Audio Data Block"; audio_block = true; break;
+	case 0x02: data_block = "Video Data Block"; break;
+	case 0x03: data_block.clear(); break;
+	case 0x04: data_block = "Speaker Allocation Data Block"; audio_block = true; break;
+	case 0x05: data_block = "VESA Display Transfer Characteristics Data Block"; break;
+
+	case 0x07: data_block.clear(); break;
+	default:
+		data_block.clear();
+		if (extended) break;
+		printf("  Unknown CTA-861 tag 0x%02x\n", tag);
+		warn("Unknown CTA-861 Data Block %u.\n", tag);
+	}
+
+	if (data_block.length())
 		printf("  %s:\n", data_block.c_str());
-		cta_svd(x, length, false);
-		break;
+
+	switch (tag) {
+	case 0x04:
+	case 0x05:
+		if (duplicate)
+			fail("Only one instance of this Data Block is allowed.\n");
+	}
+
+	// See Table 52 of CTA-861-G for a description of Byte 3
+	if (audio_block && !(cta.byte3 & 0x40))
+		fail("Audio information is present, but bit 6 of Byte 3 of the CTA-861 Extension header indicates no Basic Audio support.\n");
+
+	switch (tag) {
+	case 0x01: cta_audio_block(x, length); break;
+	case 0x02: cta_svd(x, length, false); break;
 	case 0x03:
 		data_block_o("Vendor-Specific Data Block");
 		if (oui == 0x000c03) {
@@ -2189,42 +2206,19 @@ void edid_state::cta_block(const unsigned char *x, bool duplicate)
 		}
 		hex_block("    ", x, length);
 		break;
-	case 0x04:
-		data_block = "Speaker Allocation Data Block";
-		printf("  %s:\n", data_block.c_str());
-		if (duplicate)
-			fail("Only one instance of this Data Block is allowed.\n");
-		cta_sadb(x, length);
-		audio_block = true;
-		break;
-	case 0x05:
-		data_block = "VESA Display Transfer Characteristics Data Block";
-		printf("  %s:\n", data_block.c_str());
-		if (duplicate)
-			fail("Only one instance of this Data Block is allowed.\n");
-		cta_vesa_dtcdb(x, length);
-		break;
+	case 0x04: cta_sadb(x, length); break;
+	case 0x05: cta_vesa_dtcdb(x, length); break;
 	case 0x07:
-		data_block = "Unknown CTA-861 Data Block (extended tag truncated)";
-		printf("  %s:\n", data_block.c_str());
+		printf("  Unknown CTA-861 Data Block (extended tag truncated):\n");
 		fail("Extended tag cannot have zero length.\n");
 		break;
-	default: {
-		if (extended) {
+	default:
+		if (extended)
 			cta_ext_block(tag, x, length, duplicate);
-			break;
-		}
-		printf("  Unknown CTA-861 tag 0x%02x\n", tag);
-		hex_block("    ", x, length);
-		data_block.clear();
-		warn("Unknown CTA-861 Data Block %u.\n", tag);
-		break;
-	}
+		else
+			hex_block("    ", x, length);
 	}
 
-	// See Table 52 of CTA-861-G for a description of Byte 3
-	if (audio_block && !(cta.byte3 & 0x40))
-		fail("Audio information is present, but bit 6 of Byte 3 of the CTA-861 Extension header indicates no Basic Audio support.\n");
 	cta.first_block = 0;
 	cta.last_block_was_hdmi_vsdb = 0;
 }
-- 
2.24.3 (Apple Git-128)


^ permalink raw reply related	[flat|nested] 21+ messages in thread

* [PATCH 14/28] edid-decode: remove cta_ext_block
  2021-09-24 23:31 [PATCH 00/28] bug fixes, additions, changes joevt
                   ` (12 preceding siblings ...)
  2021-09-24 23:31 ` [PATCH 13/28] edid-decode: move unknown block warning joevt
@ 2021-09-24 23:31 ` joevt
  2021-09-24 23:31 ` [PATCH 15/28] edid-decode: change unknown CTA block names joevt
                   ` (5 subsequent siblings)
  19 siblings, 0 replies; 21+ messages in thread
From: joevt @ 2021-09-24 23:31 UTC (permalink / raw)
  To: Hans Verkuil; +Cc: linux-media

Since cta_ext_block is exactly like cta_block now, we can move its code (mostly without modification) to cta_block. This way it's easier to ensure that the blocks are handled consistently (order of statements, including fails, warnings, defaults, etc.)

This change should not affect output.

Signed-off-by: Joe van Tunen <joevt@shaw.ca>
---
 edid-decode.h       |   1 -
 parse-cta-block.cpp | 187 +++++++++++++++++++-------------------------
 2 files changed, 80 insertions(+), 108 deletions(-)

diff --git a/edid-decode.h b/edid-decode.h
index ca130c5..8cb5ee7 100644
--- a/edid-decode.h
+++ b/edid-decode.h
@@ -346,7 +346,6 @@ struct edid_state {
 	void cta_displayid_type_7(const unsigned char *x, unsigned length);
 	void cta_displayid_type_8(const unsigned char *x, unsigned length);
 	void cta_displayid_type_10(const unsigned char *x, unsigned length);
-	void cta_ext_block(unsigned tag, const unsigned char *x, unsigned length, bool duplicate);
 	void cta_block(const unsigned char *x, bool duplicate);
 	void preparse_cta_block(const unsigned char *x);
 	void parse_cta_block(const unsigned char *x);
diff --git a/parse-cta-block.cpp b/parse-cta-block.cpp
index be76903..a53dc43 100644
--- a/parse-cta-block.cpp
+++ b/parse-cta-block.cpp
@@ -1998,13 +1998,31 @@ static void cta_hdmi_audio_block(const unsigned char *x, unsigned length)
 		length -= (length < 3) ? length : 3; \
 	} while(0)
 
-void edid_state::cta_ext_block(unsigned tag, const unsigned char *x, unsigned length,
-			       bool duplicate)
+void edid_state::cta_block(const unsigned char *x, bool duplicate)
 {
+	unsigned length = x[0] & 0x1f;
+	unsigned tag=(x[0] & 0xe0) >> 5;
+	unsigned extended = (tag == 0x07) ? 1 : 0;
+	x++;
+	if (extended && length) {
+		tag <<= 8;
+		tag |= x[0];
+		length--;
+		x++;
+	}
+
 	unsigned oui;
 	bool audio_block = false;
 
 	switch (tag) {
+	case 0x01: data_block = "Audio Data Block"; audio_block = true; break;
+	case 0x02: data_block = "Video Data Block"; break;
+	case 0x03: data_block.clear(); break;
+	case 0x04: data_block = "Speaker Allocation Data Block"; audio_block = true; break;
+	case 0x05: data_block = "VESA Display Transfer Characteristics Data Block"; break;
+
+	case 0x07: data_block.clear(); break;
+
 	case 0x700: data_block = "Video Capability Data Block"; break;
 	case 0x701: data_block.clear(); break;
 	case 0x702: data_block = "VESA Video Display Device Data Block"; break;
@@ -2031,24 +2049,33 @@ void edid_state::cta_ext_block(unsigned tag, const unsigned char *x, unsigned le
 
 	case 0x778: data_block = "HDMI Forum EDID Extension Override Data Block"; break;
 	case 0x779: data_block = "HDMI Forum Sink Capability Data Block"; break;
+
 	default:
 		data_block.clear();
-		if (tag < 0x70d)
-			printf("  Unknown CTA-861 Video-Related");
-		else if (tag < 0x720)
-			printf("  Unknown CTA-861 Audio-Related");
-		else if (tag >= 0x778 && tag <= 0x77f)
-			printf("  Unknown CTA-861 HDMI-Related");
-		else
-			printf("  Unknown CTA-861");
-		printf(" Data Block (extended tag 0x%02x)\n", tag & 0xff);
-		warn("Unknown Extended CTA-861 Data Block 0x%02x.\n", tag & 0xff);
+		if (tag < 0x700) {
+			printf("  Unknown CTA-861 tag 0x%02x\n", tag);
+			warn("Unknown CTA-861 Data Block %u.\n", tag);
+		}
+		else {
+			if (tag < 0x70d)
+				printf("  Unknown CTA-861 Video-Related");
+			else if (tag < 0x720)
+				printf("  Unknown CTA-861 Audio-Related");
+			else if (tag >= 0x778 && tag <= 0x77f)
+				printf("  Unknown CTA-861 HDMI-Related");
+			else
+				printf("  Unknown CTA-861");
+			printf(" Data Block (extended tag 0x%02x)\n", tag & 0xff);
+			warn("Unknown Extended CTA-861 Data Block 0x%02x.\n", tag & 0xff);
+		}
 	}
 
 	if (data_block.length())
 		printf("  %s:\n", data_block.c_str());
 
 	switch (tag) {
+	case 0x04:
+	case 0x05:
 	case 0x700:
 	case 0x702:
 	case 0x705:
@@ -2068,6 +2095,47 @@ void edid_state::cta_ext_block(unsigned tag, const unsigned char *x, unsigned le
 		fail("Audio information is present, but bit 6 of Byte 3 of the CTA-861 Extension header indicates no Basic Audio support.\n");
 
 	switch (tag) {
+	case 0x01: cta_audio_block(x, length); break;
+	case 0x02: cta_svd(x, length, false); break;
+	case 0x03:
+		data_block_o("Vendor-Specific Data Block");
+		if (oui == 0x000c03) {
+			cta_hdmi_block(x, length);
+			cta.last_block_was_hdmi_vsdb = 1;
+			cta.first_block = 0;
+			// The HDMI OUI is present, so this EDID represents an HDMI
+			// interface. And HDMI interfaces must use EDID version 1.3
+			// according to the HDMI Specification, so check for this.
+			if (base.edid_minor != 3)
+				fail("The HDMI Specification requires EDID 1.3 instead of 1.%u.\n",
+				     base.edid_minor);
+			return;
+		}
+		if (oui == 0xc45dd8) {
+			if (!cta.last_block_was_hdmi_vsdb)
+				fail("HDMI Forum VSDB did not immediately follow the HDMI VSDB.\n");
+			if (cta.have_hf_scdb || cta.have_hf_vsdb)
+				fail("Duplicate HDMI Forum VSDB/SCDB.\n");
+			cta_hf_scdb(x, length);
+			cta.have_hf_vsdb = 1;
+			break;
+		}
+		if (oui == 0x00001a) {
+			cta_amd(x, length);
+			break;
+		}
+		if (oui == 0xca125c && length == 0x12) {
+			cta_microsoft(x, length);
+			break;
+		}
+		hex_block("    ", x, length);
+		break;
+	case 0x04: cta_sadb(x, length); break;
+	case 0x05: cta_vesa_dtcdb(x, length); break;
+	case 0x07:
+		printf("  Unknown CTA-861 Data Block (extended tag truncated):\n");
+		fail("Extended tag cannot have zero length.\n");
+		break;
 	case 0x700: cta_vcdb(x, length); break;
 	case 0x701:
 		data_block_o("Vendor-Specific Video Data Block");
@@ -2123,101 +2191,6 @@ void edid_state::cta_ext_block(unsigned tag, const unsigned char *x, unsigned le
 	default:
 		hex_block("    ", x, length);
 	}
-}
-
-void edid_state::cta_block(const unsigned char *x, bool duplicate)
-{
-	unsigned length = x[0] & 0x1f;
-	unsigned tag=(x[0] & 0xe0) >> 5;
-	unsigned extended = (tag == 0x07) ? 1 : 0;
-	x++;
-	if (extended && length) {
-		tag <<= 8;
-		tag |= x[0];
-		length--;
-		x++;
-	}
-
-	unsigned oui;
-	bool audio_block = false;
-
-	switch (tag) {
-	case 0x01: data_block = "Audio Data Block"; audio_block = true; break;
-	case 0x02: data_block = "Video Data Block"; break;
-	case 0x03: data_block.clear(); break;
-	case 0x04: data_block = "Speaker Allocation Data Block"; audio_block = true; break;
-	case 0x05: data_block = "VESA Display Transfer Characteristics Data Block"; break;
-
-	case 0x07: data_block.clear(); break;
-	default:
-		data_block.clear();
-		if (extended) break;
-		printf("  Unknown CTA-861 tag 0x%02x\n", tag);
-		warn("Unknown CTA-861 Data Block %u.\n", tag);
-	}
-
-	if (data_block.length())
-		printf("  %s:\n", data_block.c_str());
-
-	switch (tag) {
-	case 0x04:
-	case 0x05:
-		if (duplicate)
-			fail("Only one instance of this Data Block is allowed.\n");
-	}
-
-	// See Table 52 of CTA-861-G for a description of Byte 3
-	if (audio_block && !(cta.byte3 & 0x40))
-		fail("Audio information is present, but bit 6 of Byte 3 of the CTA-861 Extension header indicates no Basic Audio support.\n");
-
-	switch (tag) {
-	case 0x01: cta_audio_block(x, length); break;
-	case 0x02: cta_svd(x, length, false); break;
-	case 0x03:
-		data_block_o("Vendor-Specific Data Block");
-		if (oui == 0x000c03) {
-			cta_hdmi_block(x, length);
-			cta.last_block_was_hdmi_vsdb = 1;
-			cta.first_block = 0;
-			// The HDMI OUI is present, so this EDID represents an HDMI
-			// interface. And HDMI interfaces must use EDID version 1.3
-			// according to the HDMI Specification, so check for this.
-			if (base.edid_minor != 3)
-				fail("The HDMI Specification requires EDID 1.3 instead of 1.%u.\n",
-				     base.edid_minor);
-			return;
-		}
-		if (oui == 0xc45dd8) {
-			if (!cta.last_block_was_hdmi_vsdb)
-				fail("HDMI Forum VSDB did not immediately follow the HDMI VSDB.\n");
-			if (cta.have_hf_scdb || cta.have_hf_vsdb)
-				fail("Duplicate HDMI Forum VSDB/SCDB.\n");
-			cta_hf_scdb(x, length);
-			cta.have_hf_vsdb = 1;
-			break;
-		}
-		if (oui == 0x00001a) {
-			cta_amd(x, length);
-			break;
-		}
-		if (oui == 0xca125c && length == 0x12) {
-			cta_microsoft(x, length);
-			break;
-		}
-		hex_block("    ", x, length);
-		break;
-	case 0x04: cta_sadb(x, length); break;
-	case 0x05: cta_vesa_dtcdb(x, length); break;
-	case 0x07:
-		printf("  Unknown CTA-861 Data Block (extended tag truncated):\n");
-		fail("Extended tag cannot have zero length.\n");
-		break;
-	default:
-		if (extended)
-			cta_ext_block(tag, x, length, duplicate);
-		else
-			hex_block("    ", x, length);
-	}
 
 	cta.first_block = 0;
 	cta.last_block_was_hdmi_vsdb = 0;
-- 
2.24.3 (Apple Git-128)


^ permalink raw reply related	[flat|nested] 21+ messages in thread

* [PATCH 15/28] edid-decode: change unknown CTA block names
  2021-09-24 23:31 [PATCH 00/28] bug fixes, additions, changes joevt
                   ` (13 preceding siblings ...)
  2021-09-24 23:31 ` [PATCH 14/28] edid-decode: remove cta_ext_block joevt
@ 2021-09-24 23:31 ` joevt
  2021-09-24 23:31 ` [PATCH 16/28] edid-decode: move audio fail/warn messages joevt
                   ` (4 subsequent siblings)
  19 siblings, 0 replies; 21+ messages in thread
From: joevt @ 2021-09-24 23:31 UTC (permalink / raw)
  To: Hans Verkuil; +Cc: linux-media

Make consistent the Unknown CTA-861 Data Block names and warnings.

- Add " Data Block" suffix for normal tags (like unknown extended tags and known normal tags have).
- Put tag in parenthesis (like unknown extended tags).
- Output colon after unknown block name (like known tags).
- Make warning same as block name (so the block mentioned in the warning section can be found more easily in the edid output).

1) Unknown normal tags:
Before:
- name: "Unknown CTA-861 tag 0x$$"
- warning: "Unknown CTA-861 Data Block #."
After:
"Unknown CTA-861 Data Block (tag 0x$$):" (with period instead of colon for warning)

2) Unknown extended tags:
Before:
- name: "Unknown CTA-861 @Data Block (extended tag 0x$$)" (@ = "", "Video-Related ", "Audio-Related ", "HDMI-Related ")
- warning: "Unknown Extended CTA-861 Data Block 0x$$."
After:
- "Unknown CTA-861 @Data Block (extended tag 0x$$):" (with period instead of colon for warning)

We still have the following from a previous commit:
3) Truncated extended tag (when length is not enough to get the extended tag):
Before:
name: "Unknown CTA-861 Data Block (extended tag truncated):"
failure: "Extended tag cannot have zero length."

Since the name is different than the failure message, we should set data_block so both are output to the failure section:
After:
failure: "Unknown CTA-861 Data Block (extended tag truncated): Extended tag cannot have zero length."

Signed-off-by: Joe van Tunen <joevt@shaw.ca>
---
 parse-cta-block.cpp | 33 ++++++++++++---------------------
 1 file changed, 12 insertions(+), 21 deletions(-)

diff --git a/parse-cta-block.cpp b/parse-cta-block.cpp
index a53dc43..a3690d7 100644
--- a/parse-cta-block.cpp
+++ b/parse-cta-block.cpp
@@ -2021,7 +2021,7 @@ void edid_state::cta_block(const unsigned char *x, bool duplicate)
 	case 0x04: data_block = "Speaker Allocation Data Block"; audio_block = true; break;
 	case 0x05: data_block = "VESA Display Transfer Characteristics Data Block"; break;
 
-	case 0x07: data_block.clear(); break;
+	case 0x07: data_block = "Unknown CTA-861 Data Block (extended tag truncated)"; break;
 
 	case 0x700: data_block = "Video Capability Data Block"; break;
 	case 0x701: data_block.clear(); break;
@@ -2052,22 +2052,16 @@ void edid_state::cta_block(const unsigned char *x, bool duplicate)
 
 	default:
 		data_block.clear();
-		if (tag < 0x700) {
-			printf("  Unknown CTA-861 tag 0x%02x\n", tag);
-			warn("Unknown CTA-861 Data Block %u.\n", tag);
-		}
-		else {
-			if (tag < 0x70d)
-				printf("  Unknown CTA-861 Video-Related");
-			else if (tag < 0x720)
-				printf("  Unknown CTA-861 Audio-Related");
-			else if (tag >= 0x778 && tag <= 0x77f)
-				printf("  Unknown CTA-861 HDMI-Related");
-			else
-				printf("  Unknown CTA-861");
-			printf(" Data Block (extended tag 0x%02x)\n", tag & 0xff);
-			warn("Unknown Extended CTA-861 Data Block 0x%02x.\n", tag & 0xff);
-		}
+		std::string unknown_name;
+		     if (tag < 0x700) unknown_name = "Unknown CTA-861 Data Block";
+		else if (tag < 0x70d) unknown_name = "Unknown CTA-861 Video-Related Data Block";
+		else if (tag < 0x720) unknown_name = "Unknown CTA-861 Audio-Related Data Block";
+		else if (tag < 0x778) unknown_name = "Unknown CTA-861 Data Block";
+		else if (tag < 0x780) unknown_name = "Unknown CTA-861 HDMI-Related Data Block";
+		else                  unknown_name = "Unknown CTA-861 Data Block";
+		unknown_name += std::string(" (") + (extended ? "extended " : "") + "tag " + utohex(tag & 0xff) + ")";
+		printf("  %s:\n", unknown_name.c_str());
+		warn("%s.\n", unknown_name.c_str());
 	}
 
 	if (data_block.length())
@@ -2132,10 +2126,7 @@ void edid_state::cta_block(const unsigned char *x, bool duplicate)
 		break;
 	case 0x04: cta_sadb(x, length); break;
 	case 0x05: cta_vesa_dtcdb(x, length); break;
-	case 0x07:
-		printf("  Unknown CTA-861 Data Block (extended tag truncated):\n");
-		fail("Extended tag cannot have zero length.\n");
-		break;
+	case 0x07: fail("Extended tag cannot have zero length.\n"); break;
 	case 0x700: cta_vcdb(x, length); break;
 	case 0x701:
 		data_block_o("Vendor-Specific Video Data Block");
-- 
2.24.3 (Apple Git-128)


^ permalink raw reply related	[flat|nested] 21+ messages in thread

* [PATCH 16/28] edid-decode: move audio fail/warn messages
  2021-09-24 23:31 [PATCH 00/28] bug fixes, additions, changes joevt
                   ` (14 preceding siblings ...)
  2021-09-24 23:31 ` [PATCH 15/28] edid-decode: change unknown CTA block names joevt
@ 2021-09-24 23:31 ` joevt
  2021-09-24 23:31 ` [PATCH 17/28] edid-decode: replace first_block with block_number joevt
                   ` (3 subsequent siblings)
  19 siblings, 0 replies; 21+ messages in thread
From: joevt @ 2021-09-24 23:31 UTC (permalink / raw)
  To: Hans Verkuil; +Cc: linux-media

For tag 0x711, the "Audio information is present" fail message appears before the block name. Output the block name before any fail/warning messages related to the block.

For tags that are supposed to have an OUI but are not long enough:
- Output the block name before the "Invalid length" fail message. The fail message should include the block name but we don't want cta_block to output data_block so clear it after the fail, before exiting.

For tags with a 3 byte OUI:
- Since we are calling data_block_oui early (before data_block is output in cta_block), don't output block name in data_block_oui - cta_block will do that for us.
- data_block now includes the OUI (the block name in the failure/warning section will match block name in the EDID section).

Probably things would be simpler if we always set data_block to the block name, then have fail/warning messages that don't include the block name so they don't look redundant in the failures/warnings sections. For example we could have something like:
Unknown CTA-861 Data Block (tag 0x00): Invalid tag.
Vendor-Specific Data Block, OUI $$-$$-$$: Unknown OUI.
etc.

Sample corrupted EDID (combination of vizio-e65e0-hdmi and /System/Library/Displays/Contents/Resources/Overrides/DisplayVendorID-593a/DisplayProductID-1018:edid-patches):
00ffffffffffff00593a181001010101001a0103808f50782a6a6da4554f9e270e474aa5ce00d1c0010101010101010101010101010104740030f2705a80b0588a0048684200001e023a801871382d40582c450048684200001e000000fc004536352d45310a202020202020000000fd00174c0f8c26000a202020202020014502035171575f645d625e631022201f2105041307060302111215160132570600000000000000000000090707150750830100006f030c002000383ca05b5b0060010000000061666065e3060f01e305e00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000ea

Signed-off-by: Joe van Tunen <joevt@shaw.ca>
---
 edid-decode.cpp     |  6 +++---
 parse-cta-block.cpp | 11 ++++-------
 2 files changed, 7 insertions(+), 10 deletions(-)

diff --git a/edid-decode.cpp b/edid-decode.cpp
index ec903f9..666a2c6 100644
--- a/edid-decode.cpp
+++ b/edid-decode.cpp
@@ -686,12 +686,13 @@ void edid_state::data_block_oui(const char *block_name, const unsigned char *x,
 	bool reverse = false;
 
 	if (length < 3) {
+		printf("  %s:\n", block_name);
 		data_block = std::string(block_name);
 		fail("Invalid length %u < 3.\n", length);
+		data_block.clear();
 	}
 	else {
 		oui = (x[2] << 16) + (x[1] << 8) + x[0];
-		x += 3; length -=3;
 		name = oui_name(oui);
 		if (!name) {
 			name = oui_name(oui, true);
@@ -704,10 +705,9 @@ void edid_state::data_block_oui(const char *block_name, const unsigned char *x,
 			warn("Unknown %s, OUI %s.\n", block_name, ouitohex(oui).c_str());
 		}
 		else {
-			data_block = std::string(block_name) + " (" + name + ")";
+			data_block = std::string(block_name) + " (" + name + "), OUI " + ouitohex(oui);
 			if (reverse)
 				fail((std::string("OUI ") + ouitohex(oui) + " is in the wrong byte order\n").c_str());
-			printf("  %s, OUI %s:\n", data_block.c_str(), ouitohex(oui).c_str());
 		}
 	}
 	if (ouinum) *ouinum = oui;
diff --git a/parse-cta-block.cpp b/parse-cta-block.cpp
index a3690d7..48d0013 100644
--- a/parse-cta-block.cpp
+++ b/parse-cta-block.cpp
@@ -2013,18 +2013,19 @@ void edid_state::cta_block(const unsigned char *x, bool duplicate)
 
 	unsigned oui;
 	bool audio_block = false;
+	data_block.clear();
 
 	switch (tag) {
 	case 0x01: data_block = "Audio Data Block"; audio_block = true; break;
 	case 0x02: data_block = "Video Data Block"; break;
-	case 0x03: data_block.clear(); break;
+	case 0x03: data_block_o("Vendor-Specific Data Block"); break;
 	case 0x04: data_block = "Speaker Allocation Data Block"; audio_block = true; break;
 	case 0x05: data_block = "VESA Display Transfer Characteristics Data Block"; break;
 
 	case 0x07: data_block = "Unknown CTA-861 Data Block (extended tag truncated)"; break;
 
 	case 0x700: data_block = "Video Capability Data Block"; break;
-	case 0x701: data_block.clear(); break;
+	case 0x701: data_block_o("Vendor-Specific Video Data Block"); break;
 	case 0x702: data_block = "VESA Video Display Device Data Block"; break;
 	case 0x703: data_block = "VESA Video Timing Block Extension"; break;
 	case 0x704: data_block = "Reserved for HDMI Video Data Block"; break;
@@ -2036,7 +2037,7 @@ void edid_state::cta_block(const unsigned char *x, bool duplicate)
 	case 0x70e: data_block = "YCbCr 4:2:0 Video Data Block"; break;
 	case 0x70f: data_block = "YCbCr 4:2:0 Capability Map Data Block"; break;
 	case 0x710: data_block = "Reserved for CTA-861 Miscellaneous Audio Fields"; break;
-	case 0x711: data_block.clear(); audio_block = true; break;
+	case 0x711: data_block_o("Vendor-Specific Audio Data Block"); audio_block = true; break;
 	case 0x712: data_block = "HDMI Audio Data Block"; audio_block = true; break;
 	case 0x713: data_block = "Room Configuration Data Block"; audio_block = true; break;
 	case 0x714: data_block = "Speaker Location Data Block"; audio_block = true; break;
@@ -2051,7 +2052,6 @@ void edid_state::cta_block(const unsigned char *x, bool duplicate)
 	case 0x779: data_block = "HDMI Forum Sink Capability Data Block"; break;
 
 	default:
-		data_block.clear();
 		std::string unknown_name;
 		     if (tag < 0x700) unknown_name = "Unknown CTA-861 Data Block";
 		else if (tag < 0x70d) unknown_name = "Unknown CTA-861 Video-Related Data Block";
@@ -2092,7 +2092,6 @@ void edid_state::cta_block(const unsigned char *x, bool duplicate)
 	case 0x01: cta_audio_block(x, length); break;
 	case 0x02: cta_svd(x, length, false); break;
 	case 0x03:
-		data_block_o("Vendor-Specific Data Block");
 		if (oui == 0x000c03) {
 			cta_hdmi_block(x, length);
 			cta.last_block_was_hdmi_vsdb = 1;
@@ -2129,7 +2128,6 @@ void edid_state::cta_block(const unsigned char *x, bool duplicate)
 	case 0x07: fail("Extended tag cannot have zero length.\n"); break;
 	case 0x700: cta_vcdb(x, length); break;
 	case 0x701:
-		data_block_o("Vendor-Specific Video Data Block");
 		if (oui == 0x90848b)
 			cta_hdr10plus(x, length);
 		else if (oui == 0x00d046)
@@ -2145,7 +2143,6 @@ void edid_state::cta_block(const unsigned char *x, bool duplicate)
 	case 0x70e: cta_svd(x, length, true); break;
 	case 0x70f: cta_y420cmdb(x, length); break;
 	case 0x711:
-		data_block_o("Vendor-Specific Audio Data Block");
 		if (oui == 0x00d046)
 			cta_dolby_audio(x, length);
 		else
-- 
2.24.3 (Apple Git-128)


^ permalink raw reply related	[flat|nested] 21+ messages in thread

* [PATCH 17/28] edid-decode: replace first_block with block_number
  2021-09-24 23:31 [PATCH 00/28] bug fixes, additions, changes joevt
                   ` (15 preceding siblings ...)
  2021-09-24 23:31 ` [PATCH 16/28] edid-decode: move audio fail/warn messages joevt
@ 2021-09-24 23:31 ` joevt
  2021-09-24 23:31 ` [PATCH 18/28] edid-decode: move parse_displayid_block inner loop joevt
                   ` (2 subsequent siblings)
  19 siblings, 0 replies; 21+ messages in thread
From: joevt @ 2021-09-24 23:31 UTC (permalink / raw)
  To: Hans Verkuil; +Cc: linux-media

track progress instead of milestones.

With a flag like first_block, you can only know if you're at the first block or not.
But with a progressing value like block_number, you can know when you're at the first block or second block etc. and you can know how many blocks have been done.
We'll also replace last_block_was_hdmi_vsdb in a later commit.
Both of these changes will cleanup the hdmi block.


Signed-off-by: Joe van Tunen <joevt@shaw.ca>
---
 edid-decode.h       |  5 +++--
 parse-cta-block.cpp | 10 +++++-----
 2 files changed, 8 insertions(+), 7 deletions(-)

diff --git a/edid-decode.h b/edid-decode.h
index 8cb5ee7..52d555b 100644
--- a/edid-decode.h
+++ b/edid-decode.h
@@ -154,7 +154,8 @@ struct edid_state {
 		cta.has_vic_1 = cta.first_svd_might_be_preferred = cta.has_sldb =
 			cta.has_hdmi = cta.has_vcdb = cta.has_vfpdb = false;
 		cta.last_block_was_hdmi_vsdb = cta.have_hf_vsdb = cta.have_hf_scdb = false;
-		cta.first_block = cta.first_svd = true;
+		cta.block_number = 0;
+		cta.first_svd = true;
 		cta.supported_hdmi_vic_codes = cta.supported_hdmi_vic_vsb_codes = 0;
 		memset(cta.vics, 0, sizeof(cta.vics));
 		memset(cta.preparsed_has_vic, 0, sizeof(cta.preparsed_has_vic));
@@ -259,7 +260,7 @@ struct edid_state {
 		unsigned short preparsed_phys_addr;
 		bool last_block_was_hdmi_vsdb;
 		bool have_hf_vsdb, have_hf_scdb;
-		bool first_block;
+		unsigned block_number;
 		bool first_svd;
 		unsigned supported_hdmi_vic_codes;
 		unsigned supported_hdmi_vic_vsb_codes;
diff --git a/parse-cta-block.cpp b/parse-cta-block.cpp
index 48d0013..66d8e4a 100644
--- a/parse-cta-block.cpp
+++ b/parse-cta-block.cpp
@@ -2095,7 +2095,7 @@ void edid_state::cta_block(const unsigned char *x, bool duplicate)
 		if (oui == 0x000c03) {
 			cta_hdmi_block(x, length);
 			cta.last_block_was_hdmi_vsdb = 1;
-			cta.first_block = 0;
+			cta.block_number++;
 			// The HDMI OUI is present, so this EDID represents an HDMI
 			// interface. And HDMI interfaces must use EDID version 1.3
 			// according to the HDMI Specification, so check for this.
@@ -2158,7 +2158,7 @@ void edid_state::cta_block(const unsigned char *x, bool duplicate)
 	case 0x778:
 		cta_hf_eeodb(x, length);
 		// This must be the first CTA-861 block
-		if (!cta.first_block)
+		if (cta.block_number > 0)
 			fail("Block starts at a wrong offset.\n");
 		break;
 	case 0x779:
@@ -2180,7 +2180,7 @@ void edid_state::cta_block(const unsigned char *x, bool duplicate)
 		hex_block("    ", x, length);
 	}
 
-	cta.first_block = 0;
+	cta.block_number++;
 	cta.last_block_was_hdmi_vsdb = 0;
 }
 
@@ -2297,11 +2297,11 @@ void edid_state::parse_cta_block(const unsigned char *x)
 //				msg(!cta.has_hdmi, "If YCbCr support is indicated, then both 4:2:2 and 4:4:4 %s be supported.\n",
 //				    cta.has_hdmi ? "shall" : "should");
 			printf("  Native detailed modes: %u\n", x[3] & 0x0f);
-			if (cta.first_block)
+			if (cta.block_number == 0)
 				cta.byte3 = x[3];
 			else if (x[3] != cta.byte3)
 				fail("Byte 3 must be the same for all CTA-861 Extension Blocks.\n");
-			if (cta.first_block) {
+			if (cta.block_number == 0) {
 				unsigned native_dtds = x[3] & 0x0f;
 
 				cta.native_timings.clear();
-- 
2.24.3 (Apple Git-128)


^ permalink raw reply related	[flat|nested] 21+ messages in thread

* [PATCH 18/28] edid-decode: move parse_displayid_block inner loop
  2021-09-24 23:31 [PATCH 00/28] bug fixes, additions, changes joevt
                   ` (16 preceding siblings ...)
  2021-09-24 23:31 ` [PATCH 17/28] edid-decode: replace first_block with block_number joevt
@ 2021-09-24 23:31 ` joevt
  2021-09-24 23:31 ` [PATCH 19/28] edid-decode: remove offset from displayid_block joevt
  2021-09-25  9:05 ` [PATCH 00/28] bug fixes, additions, changes Hans Verkuil
  19 siblings, 0 replies; 21+ messages in thread
From: joevt @ 2021-09-24 23:31 UTC (permalink / raw)
  To: Hans Verkuil; +Cc: linux-media

Move it to a new function displayid_block. Then we can simplify it later.
This is mostly just a copy/paste. No output should change.
The new function returns 0xff for len to signal a break from the loop in parse_displayid_block. That will be cleaned up later.

first_data_block is replaced with dispid.block_number (similar to cta.block_number)

Signed-off-by: Joe van Tunen <joevt@shaw.ca>
---
 edid-decode.h             |   3 +
 parse-displayid-block.cpp | 481 +++++++++++++++++++-------------------
 2 files changed, 247 insertions(+), 237 deletions(-)

diff --git a/edid-decode.h b/edid-decode.h
index 52d555b..b450abd 100644
--- a/edid-decode.h
+++ b/edid-decode.h
@@ -176,6 +176,7 @@ struct edid_state {
 		dispid.is_display = dispid.has_product_identification =
 			dispid.has_display_parameters = dispid.has_type_1_7 =
 			dispid.has_display_interface_features = false;
+		dispid.block_number = 0;
 
 		// Block Map block state
 		block_map.saw_block_1 = false;
@@ -283,6 +284,7 @@ struct edid_state {
 		bool has_display_interface_features;
 		vec_timings_ext preferred_timings;
 		unsigned native_width, native_height;
+		unsigned block_number;
 		// Keep track of the found CTA-861 Tag/Extended Tag pairs.
 		// The unsigned value is equal to: (tag << 8) | ext_tag
 		std::set<unsigned> found_tags;
@@ -392,6 +394,7 @@ struct edid_state {
 	void parse_displayid_type_10_timing(const unsigned char *x, unsigned sz,
 					    bool is_cta = false);
 	void preparse_displayid_block(const unsigned char *x);
+	unsigned displayid_block(const unsigned version, const unsigned char *x, unsigned offset, unsigned length);
 	void parse_displayid_block(const unsigned char *x);
 	void parse_displayid_vesa(const unsigned char *x);
 	void parse_displayid_cta_data_block(const unsigned char *x);
diff --git a/parse-displayid-block.cpp b/parse-displayid-block.cpp
index 5c81294..c0ad872 100644
--- a/parse-displayid-block.cpp
+++ b/parse-displayid-block.cpp
@@ -1609,13 +1609,254 @@ void edid_state::preparse_displayid_block(const unsigned char *x)
 	}
 }
 
+unsigned edid_state::displayid_block(const unsigned version, const unsigned char *x, unsigned offset, unsigned length)
+{
+	unsigned i;
+	unsigned tag = x[offset];
+	unsigned oui = 0;
+
+	switch (tag) {
+	// DisplayID 1.3:
+	case 0x00: data_block = "Product Identification Data Block (" + utohex(tag) + ")"; break;
+	case 0x01: data_block = "Display Parameters Data Block (" + utohex(tag) + ")"; break;
+	case 0x02: data_block = "Color Characteristics Data Block"; break;
+	case 0x03: data_block = "Video Timing Modes Type 1 - Detailed Timings Data Block"; break;
+	case 0x04: data_block = "Video Timing Modes Type 2 - Detailed Timings Data Block"; break;
+	case 0x05: data_block = "Video Timing Modes Type 3 - Short Timings Data Block"; break;
+	case 0x06: data_block = "Video Timing Modes Type 4 - DMT Timings Data Block"; break;
+	case 0x07: data_block = "Supported Timing Modes Type 1 - VESA DMT Timings Data Block"; break;
+	case 0x08: data_block = "Supported Timing Modes Type 2 - CTA-861 Timings Data Block"; break;
+	case 0x09: data_block = "Video Timing Range Data Block"; break;
+	case 0x0a: data_block = "Product Serial Number Data Block"; break;
+	case 0x0b: data_block = "GP ASCII String Data Block"; break;
+	case 0x0c: data_block = "Display Device Data Data Block"; break;
+	case 0x0d: data_block = "Interface Power Sequencing Data Block"; break;
+	case 0x0e: data_block = "Transfer Characteristics Data Block"; break;
+	case 0x0f: data_block = "Display Interface Data Block"; break;
+	case 0x10: data_block = "Stereo Display Interface Data Block (" + utohex(tag) + ")"; break;
+	case 0x11: data_block = "Video Timing Modes Type 5 - Short Timings Data Block"; break;
+	case 0x12: data_block = "Tiled Display Topology Data Block (" + utohex(tag) + ")"; break;
+	case 0x13: data_block = "Video Timing Modes Type 6 - Detailed Timings Data Block"; break;
+	// 0x14 .. 0x7e RESERVED for Additional VESA-defined Data Blocks
+	// DisplayID 2.0
+	case 0x20: data_block = "Product Identification Data Block (" + utohex(tag) + ")"; break;
+	case 0x21: data_block = "Display Parameters Data Block (" + utohex(tag) + ")"; break;
+	case 0x22: data_block = "Video Timing Modes Type 7 - Detailed Timings Data Block"; break;
+	case 0x23: data_block = "Video Timing Modes Type 8 - Enumerated Timing Codes Data Block"; break;
+	case 0x24: data_block = "Video Timing Modes Type 9 - Formula-based Timings Data Block"; break;
+	case 0x25: data_block = "Dynamic Video Timing Range Limits Data Block"; break;
+	case 0x26: data_block = "Display Interface Features Data Block"; break;
+	case 0x27: data_block = "Stereo Display Interface Data Block (" + utohex(tag) + ")"; break;
+	case 0x28: data_block = "Tiled Display Topology Data Block (" + utohex(tag) + ")"; break;
+	case 0x29: data_block = "ContainerID Data Block"; break;
+	case 0x32: data_block = "Video Timing Modes Type 10 - Formula-based Timings Data Block"; break;
+	// 0x2a .. 0x7d RESERVED for Additional VESA-defined Data Blocks
+	case 0x7e: // DisplayID 2.0
+	case 0x7f: // DisplayID 1.3
+		if ((tag == 0x7e && version >= 0x20) ||
+			(tag == 0x7f && version < 0x20)) {
+			oui = (x[offset + 3] << 16) + (x[offset + 4] << 8) + x[offset + 5];
+			const char *name = oui_name(oui);
+			bool reversed = false;
+
+			if (!name) {
+				name = oui_name(oui, true);
+				if (name)
+					reversed = true;
+			}
+			if (name)
+				data_block = std::string("Vendor-Specific Data Block (") + name + ")";
+			else
+				data_block = "Vendor-Specific Data Block, OUI " + ouitohex(oui);
+			if (reversed)
+				fail((std::string("OUI ") + ouitohex(oui) + " is in the wrong byte order.\n").c_str());
+		} else {
+			data_block = "Unknown DisplayID Data Block (" + utohex(tag) + ")";
+		}
+		break;
+	// 0x80 RESERVED
+	case 0x81: data_block = "CTA-861 DisplayID Data Block (" + utohex(tag) + ")"; break;
+	// 0x82 .. 0xff RESERVED
+	default:   data_block = "Unknown DisplayID Data Block (" + utohex(tag) + ")"; break;
+	}
+
+	if (version >= 0x20 && (tag < 0x20 || tag == 0x7f))
+		fail("Use of DisplayID v1.x tag for DisplayID v%u.%u.\n",
+			 version >> 4, version & 0xf);
+	if (version < 0x20 && tag >= 0x20 && tag <= 0x7e)
+		fail("Use of DisplayID v2.0 tag for DisplayID v%u.%u.\n",
+			 version >> 4, version & 0xf);
+
+	if (length < 3) {
+		// report a problem when the remaining bytes are not 0.
+		if (tag || x[offset + 1]) {
+			fail("Not enough bytes remain (%d) for a DisplayID data block or the DisplayID filler is non-0.\n", length);
+		}
+		return 0xff;
+	}
+
+	unsigned block_rev = x[offset + 1] & 0x07;
+	unsigned len = x[offset + 2];
+
+	if (length < len + 3) {
+		fail("The length of this DisplayID data block (%d) exceeds the number of bytes remaining (%d).\n", len + 3, length);
+		return 0xff;
+	}
+
+	if (!tag && !len) {
+		// A Product Identification Data Block with no payload bytes is not valid - assume this is the end.
+		if (!memchk(x + offset, length)) {
+			fail("Non-0 filler bytes in the DisplayID block.\n");
+		}
+		return 0xff;
+	}
+
+	printf("  %s:\n", data_block.c_str());
+
+	switch (tag) {
+	case 0x00: parse_displayid_product_id(x + offset); break;
+	case 0x01: parse_displayid_parameters(x + offset); break;
+	case 0x02: parse_displayid_color_characteristics(x + offset); break;
+	case 0x03:
+		   check_displayid_datablock_revision(x[offset + 1], 0, block_rev & 1);
+		   for (i = 0; i < len / 20; i++)
+			   parse_displayid_type_1_7_timing(&x[offset + 3 + (i * 20)], false, block_rev);
+		   break;
+	case 0x04:
+		   check_displayid_datablock_revision(x[offset + 1]);
+		   for (i = 0; i < len / 11; i++)
+			   parse_displayid_type_2_timing(&x[offset + 3 + (i * 11)]);
+		   break;
+	case 0x05:
+		   check_displayid_datablock_revision(x[offset + 1], 0, block_rev & 1);
+		   for (i = 0; i < len / 3; i++)
+			   parse_displayid_type_3_timing(&x[offset + 3 + (i * 3)]);
+		   break;
+	case 0x06:
+		   check_displayid_datablock_revision(x[offset + 1], 0xc0, 1);
+		   for (i = 0; i < len; i++)
+			   parse_displayid_type_4_8_timing((x[offset + 1] & 0xc0) >> 6, x[offset + 3 + i]);
+		   break;
+	case 0x07:
+		   check_displayid_datablock_revision(x[offset + 1]);
+		   for (i = 0; i < min(len, 10) * 8; i++)
+			   if (x[offset + 3 + i / 8] & (1 << (i % 8))) {
+				   char type[16];
+				   sprintf(type, "DMT 0x%02x", i + 1);
+				   print_timings("    ", find_dmt_id(i + 1), type);
+			   }
+		   break;
+	case 0x08:
+		   check_displayid_datablock_revision(x[offset + 1]);
+		   for (i = 0; i < min(len, 8) * 8; i++)
+			   if (x[offset + 3 + i / 8] & (1 << (i % 8))) {
+				   char type[16];
+				   sprintf(type, "VIC %3u", i + 1);
+				   print_timings("    ", find_vic_id(i + 1), type);
+			   }
+		   break;
+	case 0x09: parse_displayid_video_timing_range_limits(x + offset); break;
+	case 0x0a:
+	case 0x0b: parse_displayid_string(x + offset); break;
+	case 0x0c: parse_displayid_display_device(x + offset); break;
+	case 0x0d: parse_displayid_intf_power_sequencing(x + offset); break;
+	case 0x0e: parse_displayid_transfer_characteristics(x + offset); break;
+	case 0x0f: parse_displayid_display_intf(x + offset); break;
+	case 0x10: parse_displayid_stereo_display_intf(x + offset); break;
+	case 0x11:
+		   check_displayid_datablock_revision(x[offset + 1]);
+		   for (i = 0; i < len / 7; i++)
+			   parse_displayid_type_5_timing(&x[offset + 3 + (i * 7)]);
+		   break;
+	case 0x12: parse_displayid_tiled_display_topology(x + offset, false); break;
+	case 0x13:
+		   check_displayid_datablock_revision(x[offset + 1]);
+		   for (i = 0; i < len; i += (x[offset + 3 + i + 2] & 0x40) ? 17 : 14)
+			   parse_displayid_type_6_timing(&x[offset + 3 + i]);
+		   break;
+	case 0x20: parse_displayid_product_id(x + offset); break;
+	case 0x21:
+		   if (block_rev >= 1)
+			   check_displayid_datablock_revision(x[offset + 1], 0x80, 1);
+		   else
+			   check_displayid_datablock_revision(x[offset + 1], 0x80, 0);
+		   parse_displayid_parameters_v2(x + offset, block_rev);
+		   break;
+	case 0x22: {
+		   unsigned sz = 20;
+
+		   if (block_rev >= 2)
+			   check_displayid_datablock_revision(x[offset + 1], 0x08, 2);
+		   else if (block_rev == 1)
+			   check_displayid_datablock_revision(x[offset + 1], 0x08, 1);
+		   else
+			   check_displayid_datablock_revision(x[offset + 1]);
+		   sz += (x[offset + 1] & 0x70) >> 4;
+		   if (block_rev >= 1 && (x[offset + 1] & 0x08))
+			   printf("    These timings support DSC pass-through\n");
+		   for (i = 0; i < len / sz; i++)
+			   parse_displayid_type_1_7_timing(&x[offset + 3 + i * sz], true, block_rev);
+		   break;
+	}
+	case 0x23:
+		   if (block_rev)
+			   check_displayid_datablock_revision(x[offset + 1], 0xe8, 1);
+		   else
+			   check_displayid_datablock_revision(x[offset + 1], 0xc8);
+		   if (x[offset + 1] & 0x08) {
+			   for (i = 0; i < len / 2; i++)
+				   parse_displayid_type_4_8_timing((x[offset + 1] & 0xc0) >> 6,
+								   x[offset + 3 + i * 2] |
+								   (x[offset + 4 + i * 2] << 8));
+		   } else {
+			   for (i = 0; i < len; i++)
+				   parse_displayid_type_4_8_timing((x[offset + 1] & 0xc0) >> 6,
+								   x[offset + 3 + i]);
+		   }
+		   break;
+	case 0x24:
+		   check_displayid_datablock_revision(x[offset + 1]);
+		   for (i = 0; i < len / 6; i++)
+			   parse_displayid_type_9_timing(&x[offset + 3 + i * 6]);
+		   break;
+	case 0x25: parse_displayid_dynamic_video_timings_range_limits(x + offset); break;
+	case 0x26: parse_displayid_interface_features(x + offset); break;
+	case 0x27: parse_displayid_stereo_display_intf(x + offset); break;
+	case 0x28: parse_displayid_tiled_display_topology(x + offset, true); break;
+	case 0x29: parse_displayid_ContainerID(x + offset); break;
+	case 0x32: {
+		   unsigned sz = 6 + ((x[offset + 1] & 0x70) >> 4);
+
+		   check_displayid_datablock_revision(x[offset + 1], 0x70);
+		   for (i = 0; i < len / sz; i++)
+			   parse_displayid_type_10_timing(&x[offset + 3 + i * sz], sz);
+		   break;
+	}
+	case 0x81: parse_displayid_cta_data_block(x + offset); break;
+	case 0x7e:
+		if (oui == 0x3a0292) {
+			parse_displayid_vesa(x + offset);
+			break;
+		}
+		// fall-through
+	default: hex_block("    ", x + offset + 3, len); break;
+	}
+
+	if ((tag == 0x00 || tag == 0x20) &&
+		(!dispid.is_base_block || dispid.block_number > 0))
+		fail("%s is required to be the first DisplayID Data Block.\n",
+			 data_block.c_str());
+
+	dispid.block_number++;
+	return len;
+}
+
 void edid_state::parse_displayid_block(const unsigned char *x)
 {
 	unsigned version = x[1];
 	unsigned length = x[2];
 	unsigned prod_type = x[3]; // future check: based on type, check for required data blocks
 	unsigned ext_count = x[4];
-	unsigned i;
 
 	printf("  Version: %u.%u\n  Extension Count: %u\n",
 	       version >> 4, version & 0xf, ext_count);
@@ -1648,245 +1889,11 @@ void edid_state::parse_displayid_block(const unsigned char *x)
 	}
 
 	unsigned offset = 5;
-	bool first_data_block = true;
 	while (length > 0) {
-		unsigned tag = x[offset];
-		unsigned oui = 0;
-
-		switch (tag) {
-		// DisplayID 1.3:
-		case 0x00: data_block = "Product Identification Data Block (" + utohex(tag) + ")"; break;
-		case 0x01: data_block = "Display Parameters Data Block (" + utohex(tag) + ")"; break;
-		case 0x02: data_block = "Color Characteristics Data Block"; break;
-		case 0x03: data_block = "Video Timing Modes Type 1 - Detailed Timings Data Block"; break;
-		case 0x04: data_block = "Video Timing Modes Type 2 - Detailed Timings Data Block"; break;
-		case 0x05: data_block = "Video Timing Modes Type 3 - Short Timings Data Block"; break;
-		case 0x06: data_block = "Video Timing Modes Type 4 - DMT Timings Data Block"; break;
-		case 0x07: data_block = "Supported Timing Modes Type 1 - VESA DMT Timings Data Block"; break;
-		case 0x08: data_block = "Supported Timing Modes Type 2 - CTA-861 Timings Data Block"; break;
-		case 0x09: data_block = "Video Timing Range Data Block"; break;
-		case 0x0a: data_block = "Product Serial Number Data Block"; break;
-		case 0x0b: data_block = "GP ASCII String Data Block"; break;
-		case 0x0c: data_block = "Display Device Data Data Block"; break;
-		case 0x0d: data_block = "Interface Power Sequencing Data Block"; break;
-		case 0x0e: data_block = "Transfer Characteristics Data Block"; break;
-		case 0x0f: data_block = "Display Interface Data Block"; break;
-		case 0x10: data_block = "Stereo Display Interface Data Block (" + utohex(tag) + ")"; break;
-		case 0x11: data_block = "Video Timing Modes Type 5 - Short Timings Data Block"; break;
-		case 0x12: data_block = "Tiled Display Topology Data Block (" + utohex(tag) + ")"; break;
-		case 0x13: data_block = "Video Timing Modes Type 6 - Detailed Timings Data Block"; break;
-		// 0x14 .. 0x7e RESERVED for Additional VESA-defined Data Blocks
-		// DisplayID 2.0
-		case 0x20: data_block = "Product Identification Data Block (" + utohex(tag) + ")"; break;
-		case 0x21: data_block = "Display Parameters Data Block (" + utohex(tag) + ")"; break;
-		case 0x22: data_block = "Video Timing Modes Type 7 - Detailed Timings Data Block"; break;
-		case 0x23: data_block = "Video Timing Modes Type 8 - Enumerated Timing Codes Data Block"; break;
-		case 0x24: data_block = "Video Timing Modes Type 9 - Formula-based Timings Data Block"; break;
-		case 0x25: data_block = "Dynamic Video Timing Range Limits Data Block"; break;
-		case 0x26: data_block = "Display Interface Features Data Block"; break;
-		case 0x27: data_block = "Stereo Display Interface Data Block (" + utohex(tag) + ")"; break;
-		case 0x28: data_block = "Tiled Display Topology Data Block (" + utohex(tag) + ")"; break;
-		case 0x29: data_block = "ContainerID Data Block"; break;
-		case 0x32: data_block = "Video Timing Modes Type 10 - Formula-based Timings Data Block"; break;
-		// 0x2a .. 0x7d RESERVED for Additional VESA-defined Data Blocks
-		case 0x7e: // DisplayID 2.0
-		case 0x7f: // DisplayID 1.3
-			if ((tag == 0x7e && version >= 0x20) ||
-			    (tag == 0x7f && version < 0x20)) {
-				oui = (x[offset + 3] << 16) + (x[offset + 4] << 8) + x[offset + 5];
-				const char *name = oui_name(oui);
-				bool reversed = false;
-
-				if (!name) {
-					name = oui_name(oui, true);
-					if (name)
-						reversed = true;
-				}
-				if (name)
-					data_block = std::string("Vendor-Specific Data Block (") + name + ")";
-				else
-					data_block = "Vendor-Specific Data Block, OUI " + ouitohex(oui);
-				if (reversed)
-					fail((std::string("OUI ") + ouitohex(oui) + " is in the wrong byte order.\n").c_str());
-			} else {
-				data_block = "Unknown DisplayID Data Block (" + utohex(tag) + ")";
-			}
-			break;
-		// 0x80 RESERVED
-		case 0x81: data_block = "CTA-861 DisplayID Data Block (" + utohex(tag) + ")"; break;
-		// 0x82 .. 0xff RESERVED
-		default:   data_block = "Unknown DisplayID Data Block (" + utohex(tag) + ")"; break;
-		}
-
-		if (version >= 0x20 && (tag < 0x20 || tag == 0x7f))
-			fail("Use of DisplayID v1.x tag for DisplayID v%u.%u.\n",
-			     version >> 4, version & 0xf);
-		if (version < 0x20 && tag >= 0x20 && tag <= 0x7e)
-			fail("Use of DisplayID v2.0 tag for DisplayID v%u.%u.\n",
-			     version >> 4, version & 0xf);
-
-		if (length < 3) {
-			// report a problem when the remaining bytes are not 0.
-			if (tag || x[offset + 1]) {
-				fail("Not enough bytes remain (%d) for a DisplayID data block or the DisplayID filler is non-0.\n", length);
-			}
-			break;
-		}
-
-		unsigned block_rev = x[offset + 1] & 0x07;
-		unsigned len = x[offset + 2];
-
-		if (length < len + 3) {
-			fail("The length of this DisplayID data block (%d) exceeds the number of bytes remaining (%d).\n", len + 3, length);
-			break;
-		}
-
-		if (!tag && !len) {
-			// A Product Identification Data Block with no payload bytes is not valid - assume this is the end.
-			if (!memchk(x + offset, length)) {
-				fail("Non-0 filler bytes in the DisplayID block.\n");
-			}
-			break;
-		}
-
-		printf("  %s:\n", data_block.c_str());
-
-		switch (tag) {
-		case 0x00: parse_displayid_product_id(x + offset); break;
-		case 0x01: parse_displayid_parameters(x + offset); break;
-		case 0x02: parse_displayid_color_characteristics(x + offset); break;
-		case 0x03:
-			   check_displayid_datablock_revision(x[offset + 1], 0, block_rev & 1);
-			   for (i = 0; i < len / 20; i++)
-				   parse_displayid_type_1_7_timing(&x[offset + 3 + (i * 20)], false, block_rev);
-			   break;
-		case 0x04:
-			   check_displayid_datablock_revision(x[offset + 1]);
-			   for (i = 0; i < len / 11; i++)
-				   parse_displayid_type_2_timing(&x[offset + 3 + (i * 11)]);
-			   break;
-		case 0x05:
-			   check_displayid_datablock_revision(x[offset + 1], 0, block_rev & 1);
-			   for (i = 0; i < len / 3; i++)
-				   parse_displayid_type_3_timing(&x[offset + 3 + (i * 3)]);
-			   break;
-		case 0x06:
-			   check_displayid_datablock_revision(x[offset + 1], 0xc0, 1);
-			   for (i = 0; i < len; i++)
-				   parse_displayid_type_4_8_timing((x[offset + 1] & 0xc0) >> 6, x[offset + 3 + i]);
-			   break;
-		case 0x07:
-			   check_displayid_datablock_revision(x[offset + 1]);
-			   for (i = 0; i < min(len, 10) * 8; i++)
-				   if (x[offset + 3 + i / 8] & (1 << (i % 8))) {
-					   char type[16];
-					   sprintf(type, "DMT 0x%02x", i + 1);
-					   print_timings("    ", find_dmt_id(i + 1), type);
-				   }
-			   break;
-		case 0x08:
-			   check_displayid_datablock_revision(x[offset + 1]);
-			   for (i = 0; i < min(len, 8) * 8; i++)
-				   if (x[offset + 3 + i / 8] & (1 << (i % 8))) {
-					   char type[16];
-					   sprintf(type, "VIC %3u", i + 1);
-					   print_timings("    ", find_vic_id(i + 1), type);
-				   }
-			   break;
-		case 0x09: parse_displayid_video_timing_range_limits(x + offset); break;
-		case 0x0a:
-		case 0x0b: parse_displayid_string(x + offset); break;
-		case 0x0c: parse_displayid_display_device(x + offset); break;
-		case 0x0d: parse_displayid_intf_power_sequencing(x + offset); break;
-		case 0x0e: parse_displayid_transfer_characteristics(x + offset); break;
-		case 0x0f: parse_displayid_display_intf(x + offset); break;
-		case 0x10: parse_displayid_stereo_display_intf(x + offset); break;
-		case 0x11:
-			   check_displayid_datablock_revision(x[offset + 1]);
-			   for (i = 0; i < len / 7; i++)
-				   parse_displayid_type_5_timing(&x[offset + 3 + (i * 7)]);
-			   break;
-		case 0x12: parse_displayid_tiled_display_topology(x + offset, false); break;
-		case 0x13:
-			   check_displayid_datablock_revision(x[offset + 1]);
-			   for (i = 0; i < len; i += (x[offset + 3 + i + 2] & 0x40) ? 17 : 14)
-				   parse_displayid_type_6_timing(&x[offset + 3 + i]);
-			   break;
-		case 0x20: parse_displayid_product_id(x + offset); break;
-		case 0x21:
-			   if (block_rev >= 1)
-				   check_displayid_datablock_revision(x[offset + 1], 0x80, 1);
-			   else
-				   check_displayid_datablock_revision(x[offset + 1], 0x80, 0);
-			   parse_displayid_parameters_v2(x + offset, block_rev);
-			   break;
-		case 0x22: {
-			   unsigned sz = 20;
-
-			   if (block_rev >= 2)
-				   check_displayid_datablock_revision(x[offset + 1], 0x08, 2);
-			   else if (block_rev == 1)
-				   check_displayid_datablock_revision(x[offset + 1], 0x08, 1);
-			   else
-				   check_displayid_datablock_revision(x[offset + 1]);
-			   sz += (x[offset + 1] & 0x70) >> 4;
-			   if (block_rev >= 1 && (x[offset + 1] & 0x08))
-				   printf("    These timings support DSC pass-through\n");
-			   for (i = 0; i < len / sz; i++)
-				   parse_displayid_type_1_7_timing(&x[offset + 3 + i * sz], true, block_rev);
-			   break;
-		}
-		case 0x23:
-			   if (block_rev)
-				   check_displayid_datablock_revision(x[offset + 1], 0xe8, 1);
-			   else
-				   check_displayid_datablock_revision(x[offset + 1], 0xc8);
-			   if (x[offset + 1] & 0x08) {
-				   for (i = 0; i < len / 2; i++)
-					   parse_displayid_type_4_8_timing((x[offset + 1] & 0xc0) >> 6,
-									   x[offset + 3 + i * 2] |
-									   (x[offset + 4 + i * 2] << 8));
-			   } else {
-				   for (i = 0; i < len; i++)
-					   parse_displayid_type_4_8_timing((x[offset + 1] & 0xc0) >> 6,
-									   x[offset + 3 + i]);
-			   }
-			   break;
-		case 0x24:
-			   check_displayid_datablock_revision(x[offset + 1]);
-			   for (i = 0; i < len / 6; i++)
-				   parse_displayid_type_9_timing(&x[offset + 3 + i * 6]);
-			   break;
-		case 0x25: parse_displayid_dynamic_video_timings_range_limits(x + offset); break;
-		case 0x26: parse_displayid_interface_features(x + offset); break;
-		case 0x27: parse_displayid_stereo_display_intf(x + offset); break;
-		case 0x28: parse_displayid_tiled_display_topology(x + offset, true); break;
-		case 0x29: parse_displayid_ContainerID(x + offset); break;
-		case 0x32: {
-			   unsigned sz = 6 + ((x[offset + 1] & 0x70) >> 4);
-
-			   check_displayid_datablock_revision(x[offset + 1], 0x70);
-			   for (i = 0; i < len / sz; i++)
-				   parse_displayid_type_10_timing(&x[offset + 3 + i * sz], sz);
-			   break;
-		}
-		case 0x81: parse_displayid_cta_data_block(x + offset); break;
-		case 0x7e:
-			if (oui == 0x3a0292) {
-				parse_displayid_vesa(x + offset);
-				break;
-			}
-			// fall-through
-		default: hex_block("    ", x + offset + 3, len); break;
-		}
-
-		if ((tag == 0x00 || tag == 0x20) &&
-		    (!dispid.is_base_block || !first_data_block))
-			fail("%s is required to be the first DisplayID Data Block.\n",
-			     data_block.c_str());
+		unsigned len = displayid_block(version, x, offset, length);
+		if (len == 0xff) break;
 		length -= len + 3;
 		offset += len + 3;
-		first_data_block = false;
 	}
 
 	/*
-- 
2.24.3 (Apple Git-128)


^ permalink raw reply related	[flat|nested] 21+ messages in thread

* [PATCH 19/28] edid-decode: remove offset from displayid_block
  2021-09-24 23:31 [PATCH 00/28] bug fixes, additions, changes joevt
                   ` (17 preceding siblings ...)
  2021-09-24 23:31 ` [PATCH 18/28] edid-decode: move parse_displayid_block inner loop joevt
@ 2021-09-24 23:31 ` joevt
  2021-09-25  9:05 ` [PATCH 00/28] bug fixes, additions, changes Hans Verkuil
  19 siblings, 0 replies; 21+ messages in thread
From: joevt @ 2021-09-24 23:31 UTC (permalink / raw)
  To: Hans Verkuil; +Cc: linux-media

Change the function so that x points to the start of the DisplayID block.

Signed-off-by: Joe van Tunen <joevt@shaw.ca>
---
 edid-decode.h             |   2 +-
 parse-displayid-block.cpp | 134 +++++++++++++++++++-------------------
 2 files changed, 68 insertions(+), 68 deletions(-)

diff --git a/edid-decode.h b/edid-decode.h
index b450abd..d220e05 100644
--- a/edid-decode.h
+++ b/edid-decode.h
@@ -394,7 +394,7 @@ struct edid_state {
 	void parse_displayid_type_10_timing(const unsigned char *x, unsigned sz,
 					    bool is_cta = false);
 	void preparse_displayid_block(const unsigned char *x);
-	unsigned displayid_block(const unsigned version, const unsigned char *x, unsigned offset, unsigned length);
+	unsigned displayid_block(const unsigned version, const unsigned char *x, unsigned length);
 	void parse_displayid_block(const unsigned char *x);
 	void parse_displayid_vesa(const unsigned char *x);
 	void parse_displayid_cta_data_block(const unsigned char *x);
diff --git a/parse-displayid-block.cpp b/parse-displayid-block.cpp
index c0ad872..3be96f4 100644
--- a/parse-displayid-block.cpp
+++ b/parse-displayid-block.cpp
@@ -1609,10 +1609,10 @@ void edid_state::preparse_displayid_block(const unsigned char *x)
 	}
 }
 
-unsigned edid_state::displayid_block(const unsigned version, const unsigned char *x, unsigned offset, unsigned length)
+unsigned edid_state::displayid_block(const unsigned version, const unsigned char *x, unsigned length)
 {
 	unsigned i;
-	unsigned tag = x[offset];
+	unsigned tag = x[0];
 	unsigned oui = 0;
 
 	switch (tag) {
@@ -1655,7 +1655,7 @@ unsigned edid_state::displayid_block(const unsigned version, const unsigned char
 	case 0x7f: // DisplayID 1.3
 		if ((tag == 0x7e && version >= 0x20) ||
 			(tag == 0x7f && version < 0x20)) {
-			oui = (x[offset + 3] << 16) + (x[offset + 4] << 8) + x[offset + 5];
+			oui = (x[3] << 16) + (x[4] << 8) + x[5];
 			const char *name = oui_name(oui);
 			bool reversed = false;
 
@@ -1689,14 +1689,14 @@ unsigned edid_state::displayid_block(const unsigned version, const unsigned char
 
 	if (length < 3) {
 		// report a problem when the remaining bytes are not 0.
-		if (tag || x[offset + 1]) {
+		if (tag || x[1]) {
 			fail("Not enough bytes remain (%d) for a DisplayID data block or the DisplayID filler is non-0.\n", length);
 		}
 		return 0xff;
 	}
 
-	unsigned block_rev = x[offset + 1] & 0x07;
-	unsigned len = x[offset + 2];
+	unsigned block_rev = x[1] & 0x07;
+	unsigned len = x[2];
 
 	if (length < len + 3) {
 		fail("The length of this DisplayID data block (%d) exceeds the number of bytes remaining (%d).\n", len + 3, length);
@@ -1705,7 +1705,7 @@ unsigned edid_state::displayid_block(const unsigned version, const unsigned char
 
 	if (!tag && !len) {
 		// A Product Identification Data Block with no payload bytes is not valid - assume this is the end.
-		if (!memchk(x + offset, length)) {
+		if (!memchk(x, length)) {
 			fail("Non-0 filler bytes in the DisplayID block.\n");
 		}
 		return 0xff;
@@ -1714,132 +1714,132 @@ unsigned edid_state::displayid_block(const unsigned version, const unsigned char
 	printf("  %s:\n", data_block.c_str());
 
 	switch (tag) {
-	case 0x00: parse_displayid_product_id(x + offset); break;
-	case 0x01: parse_displayid_parameters(x + offset); break;
-	case 0x02: parse_displayid_color_characteristics(x + offset); break;
+	case 0x00: parse_displayid_product_id(x); break;
+	case 0x01: parse_displayid_parameters(x); break;
+	case 0x02: parse_displayid_color_characteristics(x); break;
 	case 0x03:
-		   check_displayid_datablock_revision(x[offset + 1], 0, block_rev & 1);
+		   check_displayid_datablock_revision(x[1], 0, block_rev & 1);
 		   for (i = 0; i < len / 20; i++)
-			   parse_displayid_type_1_7_timing(&x[offset + 3 + (i * 20)], false, block_rev);
+			   parse_displayid_type_1_7_timing(&x[3 + (i * 20)], false, block_rev);
 		   break;
 	case 0x04:
-		   check_displayid_datablock_revision(x[offset + 1]);
+		   check_displayid_datablock_revision(x[1]);
 		   for (i = 0; i < len / 11; i++)
-			   parse_displayid_type_2_timing(&x[offset + 3 + (i * 11)]);
+			   parse_displayid_type_2_timing(&x[3 + (i * 11)]);
 		   break;
 	case 0x05:
-		   check_displayid_datablock_revision(x[offset + 1], 0, block_rev & 1);
+		   check_displayid_datablock_revision(x[1], 0, block_rev & 1);
 		   for (i = 0; i < len / 3; i++)
-			   parse_displayid_type_3_timing(&x[offset + 3 + (i * 3)]);
+			   parse_displayid_type_3_timing(&x[3 + (i * 3)]);
 		   break;
 	case 0x06:
-		   check_displayid_datablock_revision(x[offset + 1], 0xc0, 1);
+		   check_displayid_datablock_revision(x[1], 0xc0, 1);
 		   for (i = 0; i < len; i++)
-			   parse_displayid_type_4_8_timing((x[offset + 1] & 0xc0) >> 6, x[offset + 3 + i]);
+			   parse_displayid_type_4_8_timing((x[1] & 0xc0) >> 6, x[3 + i]);
 		   break;
 	case 0x07:
-		   check_displayid_datablock_revision(x[offset + 1]);
+		   check_displayid_datablock_revision(x[1]);
 		   for (i = 0; i < min(len, 10) * 8; i++)
-			   if (x[offset + 3 + i / 8] & (1 << (i % 8))) {
+			   if (x[3 + i / 8] & (1 << (i % 8))) {
 				   char type[16];
 				   sprintf(type, "DMT 0x%02x", i + 1);
 				   print_timings("    ", find_dmt_id(i + 1), type);
 			   }
 		   break;
 	case 0x08:
-		   check_displayid_datablock_revision(x[offset + 1]);
+		   check_displayid_datablock_revision(x[1]);
 		   for (i = 0; i < min(len, 8) * 8; i++)
-			   if (x[offset + 3 + i / 8] & (1 << (i % 8))) {
+			   if (x[3 + i / 8] & (1 << (i % 8))) {
 				   char type[16];
 				   sprintf(type, "VIC %3u", i + 1);
 				   print_timings("    ", find_vic_id(i + 1), type);
 			   }
 		   break;
-	case 0x09: parse_displayid_video_timing_range_limits(x + offset); break;
+	case 0x09: parse_displayid_video_timing_range_limits(x); break;
 	case 0x0a:
-	case 0x0b: parse_displayid_string(x + offset); break;
-	case 0x0c: parse_displayid_display_device(x + offset); break;
-	case 0x0d: parse_displayid_intf_power_sequencing(x + offset); break;
-	case 0x0e: parse_displayid_transfer_characteristics(x + offset); break;
-	case 0x0f: parse_displayid_display_intf(x + offset); break;
-	case 0x10: parse_displayid_stereo_display_intf(x + offset); break;
+	case 0x0b: parse_displayid_string(x); break;
+	case 0x0c: parse_displayid_display_device(x); break;
+	case 0x0d: parse_displayid_intf_power_sequencing(x); break;
+	case 0x0e: parse_displayid_transfer_characteristics(x); break;
+	case 0x0f: parse_displayid_display_intf(x); break;
+	case 0x10: parse_displayid_stereo_display_intf(x); break;
 	case 0x11:
-		   check_displayid_datablock_revision(x[offset + 1]);
+		   check_displayid_datablock_revision(x[1]);
 		   for (i = 0; i < len / 7; i++)
-			   parse_displayid_type_5_timing(&x[offset + 3 + (i * 7)]);
+			   parse_displayid_type_5_timing(&x[3 + (i * 7)]);
 		   break;
-	case 0x12: parse_displayid_tiled_display_topology(x + offset, false); break;
+	case 0x12: parse_displayid_tiled_display_topology(x, false); break;
 	case 0x13:
-		   check_displayid_datablock_revision(x[offset + 1]);
-		   for (i = 0; i < len; i += (x[offset + 3 + i + 2] & 0x40) ? 17 : 14)
-			   parse_displayid_type_6_timing(&x[offset + 3 + i]);
+		   check_displayid_datablock_revision(x[1]);
+		   for (i = 0; i < len; i += (x[3 + i + 2] & 0x40) ? 17 : 14)
+			   parse_displayid_type_6_timing(&x[3 + i]);
 		   break;
-	case 0x20: parse_displayid_product_id(x + offset); break;
+	case 0x20: parse_displayid_product_id(x); break;
 	case 0x21:
 		   if (block_rev >= 1)
-			   check_displayid_datablock_revision(x[offset + 1], 0x80, 1);
+			   check_displayid_datablock_revision(x[1], 0x80, 1);
 		   else
-			   check_displayid_datablock_revision(x[offset + 1], 0x80, 0);
-		   parse_displayid_parameters_v2(x + offset, block_rev);
+			   check_displayid_datablock_revision(x[1], 0x80, 0);
+		   parse_displayid_parameters_v2(x, block_rev);
 		   break;
 	case 0x22: {
 		   unsigned sz = 20;
 
 		   if (block_rev >= 2)
-			   check_displayid_datablock_revision(x[offset + 1], 0x08, 2);
+			   check_displayid_datablock_revision(x[1], 0x08, 2);
 		   else if (block_rev == 1)
-			   check_displayid_datablock_revision(x[offset + 1], 0x08, 1);
+			   check_displayid_datablock_revision(x[1], 0x08, 1);
 		   else
-			   check_displayid_datablock_revision(x[offset + 1]);
-		   sz += (x[offset + 1] & 0x70) >> 4;
-		   if (block_rev >= 1 && (x[offset + 1] & 0x08))
+			   check_displayid_datablock_revision(x[1]);
+		   sz += (x[1] & 0x70) >> 4;
+		   if (block_rev >= 1 && (x[1] & 0x08))
 			   printf("    These timings support DSC pass-through\n");
 		   for (i = 0; i < len / sz; i++)
-			   parse_displayid_type_1_7_timing(&x[offset + 3 + i * sz], true, block_rev);
+			   parse_displayid_type_1_7_timing(&x[3 + i * sz], true, block_rev);
 		   break;
 	}
 	case 0x23:
 		   if (block_rev)
-			   check_displayid_datablock_revision(x[offset + 1], 0xe8, 1);
+			   check_displayid_datablock_revision(x[1], 0xe8, 1);
 		   else
-			   check_displayid_datablock_revision(x[offset + 1], 0xc8);
-		   if (x[offset + 1] & 0x08) {
+			   check_displayid_datablock_revision(x[1], 0xc8);
+		   if (x[1] & 0x08) {
 			   for (i = 0; i < len / 2; i++)
-				   parse_displayid_type_4_8_timing((x[offset + 1] & 0xc0) >> 6,
-								   x[offset + 3 + i * 2] |
-								   (x[offset + 4 + i * 2] << 8));
+				   parse_displayid_type_4_8_timing((x[1] & 0xc0) >> 6,
+								   x[3 + i * 2] |
+								   (x[4 + i * 2] << 8));
 		   } else {
 			   for (i = 0; i < len; i++)
-				   parse_displayid_type_4_8_timing((x[offset + 1] & 0xc0) >> 6,
-								   x[offset + 3 + i]);
+				   parse_displayid_type_4_8_timing((x[1] & 0xc0) >> 6,
+								   x[3 + i]);
 		   }
 		   break;
 	case 0x24:
-		   check_displayid_datablock_revision(x[offset + 1]);
+		   check_displayid_datablock_revision(x[1]);
 		   for (i = 0; i < len / 6; i++)
-			   parse_displayid_type_9_timing(&x[offset + 3 + i * 6]);
+			   parse_displayid_type_9_timing(&x[3 + i * 6]);
 		   break;
-	case 0x25: parse_displayid_dynamic_video_timings_range_limits(x + offset); break;
-	case 0x26: parse_displayid_interface_features(x + offset); break;
-	case 0x27: parse_displayid_stereo_display_intf(x + offset); break;
-	case 0x28: parse_displayid_tiled_display_topology(x + offset, true); break;
-	case 0x29: parse_displayid_ContainerID(x + offset); break;
+	case 0x25: parse_displayid_dynamic_video_timings_range_limits(x); break;
+	case 0x26: parse_displayid_interface_features(x); break;
+	case 0x27: parse_displayid_stereo_display_intf(x); break;
+	case 0x28: parse_displayid_tiled_display_topology(x, true); break;
+	case 0x29: parse_displayid_ContainerID(x); break;
 	case 0x32: {
-		   unsigned sz = 6 + ((x[offset + 1] & 0x70) >> 4);
+		   unsigned sz = 6 + ((x[1] & 0x70) >> 4);
 
-		   check_displayid_datablock_revision(x[offset + 1], 0x70);
+		   check_displayid_datablock_revision(x[1], 0x70);
 		   for (i = 0; i < len / sz; i++)
-			   parse_displayid_type_10_timing(&x[offset + 3 + i * sz], sz);
+			   parse_displayid_type_10_timing(&x[3 + i * sz], sz);
 		   break;
 	}
-	case 0x81: parse_displayid_cta_data_block(x + offset); break;
+	case 0x81: parse_displayid_cta_data_block(x); break;
 	case 0x7e:
 		if (oui == 0x3a0292) {
-			parse_displayid_vesa(x + offset);
+			parse_displayid_vesa(x);
 			break;
 		}
 		// fall-through
-	default: hex_block("    ", x + offset + 3, len); break;
+	default: hex_block("    ", x + 3, len); break;
 	}
 
 	if ((tag == 0x00 || tag == 0x20) &&
@@ -1890,7 +1890,7 @@ void edid_state::parse_displayid_block(const unsigned char *x)
 
 	unsigned offset = 5;
 	while (length > 0) {
-		unsigned len = displayid_block(version, x, offset, length);
+		unsigned len = displayid_block(version, x + offset, length);
 		if (len == 0xff) break;
 		length -= len + 3;
 		offset += len + 3;
-- 
2.24.3 (Apple Git-128)


^ permalink raw reply related	[flat|nested] 21+ messages in thread

* Re: [PATCH 00/28] bug fixes, additions, changes
  2021-09-24 23:31 [PATCH 00/28] bug fixes, additions, changes joevt
                   ` (18 preceding siblings ...)
  2021-09-24 23:31 ` [PATCH 19/28] edid-decode: remove offset from displayid_block joevt
@ 2021-09-25  9:05 ` Hans Verkuil
  19 siblings, 0 replies; 21+ messages in thread
From: Hans Verkuil @ 2021-09-25  9:05 UTC (permalink / raw)
  To: joevt; +Cc: linux-media

Hi Joe,

This series is missing patches 20-28 (at least, I never received them, and neither
did they appear on the linux-media mailinglist).

It also needs to be rebased to the latest edid-decode git repo master branch since
it no longer applies.

Regards,

	Hans

On 25/09/2021 01:31, joevt wrote:
> - Patch 02/28 replaces my previous patch 05/11.
> It adds a new warning message.
> 
> - The problem with my previous patch 07/11 is addressed in patch 01/28 and 04/28 (and maybe elsewhere).
> 
> - Patches 06/28 to 26/28 replace my previous patch 11/11 (broken down into smaller steps this time).
> They contain some corrections.
> 
> - Includes some other changes.
> 
> 
> joevt (28):
>   edid-decode: remove unnecessary length check
>   edid-decode: fix standard timing vertical pixels
>   edid-decode: exclude oui from _block functions
>   edid-decode: check cta_hdr10plus length
>   edid-decode: Capitalize fail sentence
>   edid-decode: Replace return with break in switch
>   edid-decode: extended tag length check
>   edid-decode: Output block type before fail
>   edid-decode: update Microsoft expected length
>   edid-decode: Capitalize fail sentence
>   edid-decode: make all OUI handlers the same
>   edid-decode: move OUI parsing to separate function
>   edid-decode: move unknown block warning
>   edid-decode: remove cta_ext_block
>   edid-decode: change unknown CTA block names
>   edid-decode: move audio fail/warn messages
>   edid-decode: replace first_block with block_number
>   edid-decode: move parse_displayid_block inner loop
>   edid-decode: remove offset from displayid_block
>   edid-decode: displayid_block len fixes
>   edid-decode: ignore DisplayID version for OUI check.
>   edid-decode: DisplayID non-0 filler fixes
>   edid-decode: DisplayID length checks
>   edid-decode: make OUI enum
>   edid-decode: more OUI changes
>   edid-decode: remove extra vendor field
>   edid-decode: re-add one EDID
>   edid-decode: add interesting EDID
> 
>  data/apple-imac-retina-4k-21.5-inch-late-2015 | Bin 0 -> 256 bytes
>  data/vizio-m60c3-hdmi-onkyo-txnr555           | Bin 0 -> 256 bytes
>  edid-decode.cpp                               | 106 +++-
>  edid-decode.h                                 |  32 +-
>  oui.h                                         |  20 +
>  parse-base-block.cpp                          |   5 +-
>  parse-cta-block.cpp                           | 482 +++++++----------
>  parse-displayid-block.cpp                     | 498 +++++++++---------
>  8 files changed, 553 insertions(+), 590 deletions(-)
>  create mode 100644 data/apple-imac-retina-4k-21.5-inch-late-2015
>  create mode 100644 oui.h
> 


^ permalink raw reply	[flat|nested] 21+ messages in thread

end of thread, other threads:[~2021-09-25  9:06 UTC | newest]

Thread overview: 21+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2021-09-24 23:31 [PATCH 00/28] bug fixes, additions, changes joevt
2021-09-24 23:31 ` [PATCH 01/28] edid-decode: remove unnecessary length check joevt
2021-09-24 23:31 ` [PATCH 02/28] edid-decode: fix standard timing vertical pixels joevt
2021-09-24 23:31 ` [PATCH 03/28] edid-decode: exclude oui from _block functions joevt
2021-09-24 23:31 ` [PATCH 04/28] edid-decode: check cta_hdr10plus length joevt
2021-09-24 23:31 ` [PATCH 05/28] edid-decode: Capitalize fail sentence joevt
2021-09-24 23:31 ` [PATCH 06/28] edid-decode: Replace return with break in switch joevt
2021-09-24 23:31 ` [PATCH 07/28] edid-decode: extended tag length check joevt
2021-09-24 23:31 ` [PATCH 08/28] edid-decode: Output block type before fail joevt
2021-09-24 23:31 ` [PATCH 09/28] edid-decode: update Microsoft expected length joevt
2021-09-24 23:31 ` [PATCH 10/28] edid-decode: Capitalize fail sentence joevt
2021-09-24 23:31 ` [PATCH 11/28] edid-decode: make all OUI handlers the same joevt
2021-09-24 23:31 ` [PATCH 12/28] edid-decode: move OUI parsing to separate function joevt
2021-09-24 23:31 ` [PATCH 13/28] edid-decode: move unknown block warning joevt
2021-09-24 23:31 ` [PATCH 14/28] edid-decode: remove cta_ext_block joevt
2021-09-24 23:31 ` [PATCH 15/28] edid-decode: change unknown CTA block names joevt
2021-09-24 23:31 ` [PATCH 16/28] edid-decode: move audio fail/warn messages joevt
2021-09-24 23:31 ` [PATCH 17/28] edid-decode: replace first_block with block_number joevt
2021-09-24 23:31 ` [PATCH 18/28] edid-decode: move parse_displayid_block inner loop joevt
2021-09-24 23:31 ` [PATCH 19/28] edid-decode: remove offset from displayid_block joevt
2021-09-25  9:05 ` [PATCH 00/28] bug fixes, additions, changes Hans Verkuil

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).