produce correct color channel descriptor for 32 bit depth vesa modes. the vesa bios omits reserved byte pos/mask in the mode info for 32 bit, resulting in a r8g8b8 channel descriptor that doesnt add up in length to 32 bit depth. this patch will produce the correct x8r8g8b8 channel by assigning the unmasked part (not used by any rgb component) of a pixel word to the x channel. it also doesnt assume any channel ordering and should work for all rgb modes (16/24/32). Reference: /n/sources/patch/applied/vesa-depth32 Date: Sat Mar 5 07:21:11 CET 2011 Signed-off-by: cinap_lenrek@gmx.de --- /sys/src/cmd/aux/vga/vesa.c Sat Mar 5 07:13:44 2011 +++ /sys/src/cmd/aux/vga/vesa.c Sat Mar 5 07:13:39 2011 @@ -503,10 +503,45 @@ m->dx, m->dy, m->depth); if(m->depth <= 8) snprint(m->chan, sizeof m->chan, "m%d", m->depth); - else if(m->xo) - snprint(m->chan, sizeof m->chan, "x%dr%dg%db%d", m->x, m->r, m->g, m->b); - else - snprint(m->chan, sizeof m->chan, "r%dg%db%d", m->r, m->g, m->b); + else { + int o; + ulong d, c, x; + + m->xo = m->x = 0; + d = 1<depth-1; + d |= d-1; + c = ((1<r)-1) << m->ro; + c |= ((1<g)-1) << m->go; + c |= ((1<b)-1) << m->bo; + if(x = d ^ c){ + for(; (x & 1) == 0; x >>= 1) + m->xo++; + for(; (x & 1) == 1; x >>= 1) + m->x++; + } + + o = 0; + m->chan[0] = 0; + while(o < m->depth){ + char tmp[sizeof m->chan]; + + if(m->r && m->ro == o){ + snprint(tmp, sizeof tmp, "r%d%s", m->r, m->chan); + o += m->r; + }else if(m->g && m->go == o){ + snprint(tmp, sizeof tmp, "g%d%s", m->g, m->chan); + o += m->g; + }else if(m->b && m->bo == o){ + snprint(tmp, sizeof tmp, "b%d%s", m->b, m->chan); + o += m->b; + }else if(m->x && m->xo == o){ + snprint(tmp, sizeof tmp, "x%d%s", m->x, m->chan); + o += m->x; + }else + break; + strncpy(m->chan, tmp, sizeof m->chan); + } + } return 0; }