|
@@ -1231,6 +1231,52 @@ static void default_attr(struct vc_data *vc)
|
|
vc->vc_color = vc->vc_def_color;
|
|
vc->vc_color = vc->vc_def_color;
|
|
}
|
|
}
|
|
|
|
|
|
|
|
+struct rgb { u8 r; u8 g; u8 b; };
|
|
|
|
+
|
|
|
|
+struct rgb rgb_from_256(int i)
|
|
|
|
+{
|
|
|
|
+ struct rgb c;
|
|
|
|
+ if (i < 8) { /* Standard colours. */
|
|
|
|
+ c.r = i&1 ? 0xaa : 0x00;
|
|
|
|
+ c.g = i&2 ? 0xaa : 0x00;
|
|
|
|
+ c.b = i&4 ? 0xaa : 0x00;
|
|
|
|
+ } else if (i < 16) {
|
|
|
|
+ c.r = i&1 ? 0xff : 0x55;
|
|
|
|
+ c.g = i&2 ? 0xff : 0x55;
|
|
|
|
+ c.b = i&4 ? 0xff : 0x55;
|
|
|
|
+ } else if (i < 232) { /* 6x6x6 colour cube. */
|
|
|
|
+ c.r = (i - 16) / 36 * 85 / 2;
|
|
|
|
+ c.g = (i - 16) / 6 % 6 * 85 / 2;
|
|
|
|
+ c.b = (i - 16) % 6 * 85 / 2;
|
|
|
|
+ } else /* Grayscale ramp. */
|
|
|
|
+ c.r = c.g = c.b = i * 10 - 2312;
|
|
|
|
+ return c;
|
|
|
|
+}
|
|
|
|
+
|
|
|
|
+static void rgb_foreground(struct vc_data *vc, struct rgb c)
|
|
|
|
+{
|
|
|
|
+ u8 hue, max = c.r;
|
|
|
|
+ if (c.g > max)
|
|
|
|
+ max = c.g;
|
|
|
|
+ if (c.b > max)
|
|
|
|
+ max = c.b;
|
|
|
|
+ hue = (c.r > max/2 ? 4 : 0)
|
|
|
|
+ | (c.g > max/2 ? 2 : 0)
|
|
|
|
+ | (c.b > max/2 ? 1 : 0);
|
|
|
|
+ if (hue == 7 && max <= 0x55)
|
|
|
|
+ hue = 0, vc->vc_intensity = 2;
|
|
|
|
+ else
|
|
|
|
+ vc->vc_intensity = (max > 0xaa) + 1;
|
|
|
|
+ vc->vc_color = (vc->vc_color & 0xf0) | hue;
|
|
|
|
+}
|
|
|
|
+
|
|
|
|
+static void rgb_background(struct vc_data *vc, struct rgb c)
|
|
|
|
+{
|
|
|
|
+ /* For backgrounds, err on the dark side. */
|
|
|
|
+ vc->vc_color = (vc->vc_color & 0x0f)
|
|
|
|
+ | (c.r&0x80) >> 1 | (c.g&0x80) >> 2 | (c.b&0x80) >> 3;
|
|
|
|
+}
|
|
|
|
+
|
|
/* console_lock is held */
|
|
/* console_lock is held */
|
|
static void csi_m(struct vc_data *vc)
|
|
static void csi_m(struct vc_data *vc)
|
|
{
|
|
{
|
|
@@ -1302,8 +1348,7 @@ static void csi_m(struct vc_data *vc)
|
|
case 27:
|
|
case 27:
|
|
vc->vc_reverse = 0;
|
|
vc->vc_reverse = 0;
|
|
break;
|
|
break;
|
|
- case 38:
|
|
|
|
- case 48: /* ITU T.416
|
|
|
|
|
|
+ case 38: /* ITU T.416
|
|
* Higher colour modes.
|
|
* Higher colour modes.
|
|
* They break the usual properties of SGR codes
|
|
* They break the usual properties of SGR codes
|
|
* and thus need to be detected and ignored by
|
|
* and thus need to be detected and ignored by
|
|
@@ -1315,15 +1360,41 @@ static void csi_m(struct vc_data *vc)
|
|
i++;
|
|
i++;
|
|
if (i > vc->vc_npar)
|
|
if (i > vc->vc_npar)
|
|
break;
|
|
break;
|
|
- if (vc->vc_par[i] == 5) /* 256 colours */
|
|
|
|
- i++; /* ubiquitous */
|
|
|
|
- else if (vc->vc_par[i] == 2) /* 24 bit colours */
|
|
|
|
- i += 3; /* extremely rare */
|
|
|
|
|
|
+ if (vc->vc_par[i] == 5 && /* 256 colours */
|
|
|
|
+ i < vc->vc_npar) { /* ubiquitous */
|
|
|
|
+ i++;
|
|
|
|
+ rgb_foreground(vc,
|
|
|
|
+ rgb_from_256(vc->vc_par[i]));
|
|
|
|
+ } else if (vc->vc_par[i] == 2 && /* 24 bit */
|
|
|
|
+ i <= vc->vc_npar + 3) {/* extremely rare */
|
|
|
|
+ struct rgb c = {r:vc->vc_par[i+1],
|
|
|
|
+ g:vc->vc_par[i+2],
|
|
|
|
+ b:vc->vc_par[i+3]};
|
|
|
|
+ rgb_foreground(vc, c);
|
|
|
|
+ i += 3;
|
|
|
|
+ }
|
|
/* Subcommands 3 (CMY) and 4 (CMYK) are so insane
|
|
/* Subcommands 3 (CMY) and 4 (CMYK) are so insane
|
|
- * that detecting them is not worth the few extra
|
|
|
|
- * bytes of kernel's size.
|
|
|
|
|
|
+ * there's no point in supporting them.
|
|
*/
|
|
*/
|
|
break;
|
|
break;
|
|
|
|
+ case 48:
|
|
|
|
+ i++;
|
|
|
|
+ if (i > vc->vc_npar)
|
|
|
|
+ break;
|
|
|
|
+ if (vc->vc_par[i] == 5 && /* 256 colours */
|
|
|
|
+ i < vc->vc_npar) {
|
|
|
|
+ i++;
|
|
|
|
+ rgb_background(vc,
|
|
|
|
+ rgb_from_256(vc->vc_par[i]));
|
|
|
|
+ } else if (vc->vc_par[i] == 2 && /* 24 bit */
|
|
|
|
+ i <= vc->vc_npar + 3) {
|
|
|
|
+ struct rgb c = {r:vc->vc_par[i+1],
|
|
|
|
+ g:vc->vc_par[i+2],
|
|
|
|
+ b:vc->vc_par[i+3]};
|
|
|
|
+ rgb_background(vc, c);
|
|
|
|
+ i += 3;
|
|
|
|
+ }
|
|
|
|
+ break;
|
|
case 39:
|
|
case 39:
|
|
vc->vc_color = (vc->vc_def_color & 0x0f) | (vc->vc_color & 0xf0);
|
|
vc->vc_color = (vc->vc_def_color & 0x0f) | (vc->vc_color & 0xf0);
|
|
break;
|
|
break;
|