1*83d290c5STom Rini // SPDX-License-Identifier: GPL-2.0+
250217deeSJens Scharsig /*
350217deeSJens Scharsig * (C) Copyright 2005-2009
450217deeSJens Scharsig * Jens Scharsig @ BuS Elektronik GmbH & Co. KG, <esw@bus-elektronik.de>
550217deeSJens Scharsig */
650217deeSJens Scharsig
750217deeSJens Scharsig #include <common.h>
850217deeSJens Scharsig #include <bmp_layout.h>
950217deeSJens Scharsig #include <asm/io.h>
1050217deeSJens Scharsig
1150217deeSJens Scharsig vu_char *vcxk_bws = ((vu_char *) (CONFIG_SYS_VCXK_BASE));
1250217deeSJens Scharsig vu_short *vcxk_bws_word = ((vu_short *)(CONFIG_SYS_VCXK_BASE));
1350217deeSJens Scharsig vu_long *vcxk_bws_long = ((vu_long *) (CONFIG_SYS_VCXK_BASE));
1450217deeSJens Scharsig
1550217deeSJens Scharsig #ifdef CONFIG_AT91RM9200
1650217deeSJens Scharsig #include <asm/arch/hardware.h>
170cf0b931SJens Scharsig #include <asm/arch/at91_pio.h>
180cf0b931SJens Scharsig
1950217deeSJens Scharsig #ifndef VCBITMASK
2050217deeSJens Scharsig #define VCBITMASK(bitno) (0x0001 << (bitno % 16))
2150217deeSJens Scharsig #endif
220cf0b931SJens Scharsig at91_pio_t *pio = (at91_pio_t *) AT91_PIO_BASE;
230cf0b931SJens Scharsig #define VCXK_INIT_PIN(PORT, PIN, DDR, I0O1) \
240cf0b931SJens Scharsig do { \
250cf0b931SJens Scharsig writel(PIN, &pio->PORT.per); \
260cf0b931SJens Scharsig writel(PIN, &pio->PORT.DDR); \
270cf0b931SJens Scharsig writel(PIN, &pio->PORT.mddr); \
280cf0b931SJens Scharsig if (!I0O1) \
290cf0b931SJens Scharsig writel(PIN, &pio->PORT.puer); \
300cf0b931SJens Scharsig } while (0);
310cf0b931SJens Scharsig
320cf0b931SJens Scharsig #define VCXK_SET_PIN(PORT, PIN) writel(PIN, &pio->PORT.sodr);
330cf0b931SJens Scharsig #define VCXK_CLR_PIN(PORT, PIN) writel(PIN, &pio->PORT.codr);
340cf0b931SJens Scharsig
350cf0b931SJens Scharsig #define VCXK_ACKNOWLEDGE \
360cf0b931SJens Scharsig (!(readl(&pio->CONFIG_SYS_VCXK_ACKNOWLEDGE_PORT.pdsr) & \
370cf0b931SJens Scharsig CONFIG_SYS_VCXK_ACKNOWLEDGE_PIN))
3850217deeSJens Scharsig #elif defined(CONFIG_MCF52x2)
3950217deeSJens Scharsig #include <asm/m5282.h>
4050217deeSJens Scharsig #ifndef VCBITMASK
4150217deeSJens Scharsig #define VCBITMASK(bitno) (0x8000 >> (bitno % 16))
4250217deeSJens Scharsig #endif
4350217deeSJens Scharsig
4450217deeSJens Scharsig #define VCXK_INIT_PIN(PORT, PIN, DDR, I0O1) \
4550217deeSJens Scharsig if (I0O1) DDR |= PIN; else DDR &= ~PIN;
4650217deeSJens Scharsig
4750217deeSJens Scharsig #define VCXK_SET_PIN(PORT, PIN) PORT |= PIN;
4850217deeSJens Scharsig #define VCXK_CLR_PIN(PORT, PIN) PORT &= ~PIN;
4950217deeSJens Scharsig
5050217deeSJens Scharsig #define VCXK_ACKNOWLEDGE \
5150217deeSJens Scharsig (!(CONFIG_SYS_VCXK_ACKNOWLEDGE_PORT & \
5250217deeSJens Scharsig CONFIG_SYS_VCXK_ACKNOWLEDGE_PIN))
5350217deeSJens Scharsig
5450217deeSJens Scharsig #else
5550217deeSJens Scharsig #error no vcxk support for selected ARCH
5650217deeSJens Scharsig #endif
5750217deeSJens Scharsig
5850217deeSJens Scharsig #define VCXK_DISABLE\
5950217deeSJens Scharsig VCXK_SET_PIN(CONFIG_SYS_VCXK_ENABLE_PORT, CONFIG_SYS_VCXK_ENABLE_PIN)
6050217deeSJens Scharsig #define VCXK_ENABLE\
6150217deeSJens Scharsig VCXK_CLR_PIN(CONFIG_SYS_VCXK_ENABLE_PORT, CONFIG_SYS_VCXK_ENABLE_PIN)
6250217deeSJens Scharsig
6350217deeSJens Scharsig #ifndef CONFIG_SYS_VCXK_DOUBLEBUFFERED
6450217deeSJens Scharsig #define VCXK_BWS(x, data) vcxk_bws[x] = data;
6550217deeSJens Scharsig #define VCXK_BWS_WORD_SET(x, mask) vcxk_bws_word[x] |= mask;
6650217deeSJens Scharsig #define VCXK_BWS_WORD_CLEAR(x, mask) vcxk_bws_word[x] &= ~mask;
6750217deeSJens Scharsig #define VCXK_BWS_LONG(x, data) vcxk_bws_long[x] = data;
6850217deeSJens Scharsig #else
6950217deeSJens Scharsig u_char double_bws[16384];
7050217deeSJens Scharsig u_short *double_bws_word;
7150217deeSJens Scharsig u_long *double_bws_long;
7250217deeSJens Scharsig #define VCXK_BWS(x,data) \
7350217deeSJens Scharsig double_bws[x] = data; vcxk_bws[x] = data;
7450217deeSJens Scharsig #define VCXK_BWS_WORD_SET(x,mask) \
7550217deeSJens Scharsig double_bws_word[x] |= mask; \
7650217deeSJens Scharsig vcxk_bws_word[x] = double_bws_word[x];
7750217deeSJens Scharsig #define VCXK_BWS_WORD_CLEAR(x,mask) \
7850217deeSJens Scharsig double_bws_word[x] &= ~mask; \
7950217deeSJens Scharsig vcxk_bws_word[x] = double_bws_word[x];
8050217deeSJens Scharsig #define VCXK_BWS_LONG(x,data) \
8150217deeSJens Scharsig double_bws_long[x] = data; vcxk_bws_long[x] = data;
8250217deeSJens Scharsig #endif
8350217deeSJens Scharsig
8450217deeSJens Scharsig #define VC4K16_Bright1 vcxk_bws_word[0x20004 / 2]
8550217deeSJens Scharsig #define VC4K16_Bright2 vcxk_bws_word[0x20006 / 2]
8650217deeSJens Scharsig #define VC2K_Bright vcxk_bws[0x8000]
8750217deeSJens Scharsig #define VC8K_BrightH vcxk_bws[0xC000]
8850217deeSJens Scharsig #define VC8K_BrightL vcxk_bws[0xC001]
8950217deeSJens Scharsig
9050217deeSJens Scharsig vu_char VC4K16;
9150217deeSJens Scharsig
9250217deeSJens Scharsig u_long display_width;
9350217deeSJens Scharsig u_long display_height;
9450217deeSJens Scharsig u_long display_bwidth;
9550217deeSJens Scharsig
9650217deeSJens Scharsig ulong search_vcxk_driver(void);
9750217deeSJens Scharsig void vcxk_cls(void);
9850217deeSJens Scharsig void vcxk_setbrightness(unsigned int side, short brightness);
9950217deeSJens Scharsig int vcxk_request(void);
10050217deeSJens Scharsig int vcxk_acknowledge_wait(void);
10150217deeSJens Scharsig void vcxk_clear(void);
10250217deeSJens Scharsig
10350217deeSJens Scharsig /*
10450217deeSJens Scharsig ****f* bus_vcxk/vcxk_init
10550217deeSJens Scharsig * FUNCTION
10650217deeSJens Scharsig * initialalize Video Controller
10750217deeSJens Scharsig * PARAMETERS
10850217deeSJens Scharsig * width visible display width in pixel
10950217deeSJens Scharsig * height visible display height in pixel
11050217deeSJens Scharsig ***
11150217deeSJens Scharsig */
11250217deeSJens Scharsig
vcxk_init(unsigned long width,unsigned long height)11350217deeSJens Scharsig int vcxk_init(unsigned long width, unsigned long height)
11450217deeSJens Scharsig {
11550217deeSJens Scharsig #ifdef CONFIG_SYS_VCXK_RESET_PORT
11650217deeSJens Scharsig VCXK_INIT_PIN(CONFIG_SYS_VCXK_RESET_PORT,
11750217deeSJens Scharsig CONFIG_SYS_VCXK_RESET_PIN, CONFIG_SYS_VCXK_RESET_DDR, 1)
11850217deeSJens Scharsig VCXK_SET_PIN(CONFIG_SYS_VCXK_RESET_PORT, CONFIG_SYS_VCXK_RESET_PIN);
11950217deeSJens Scharsig #endif
12050217deeSJens Scharsig
12150217deeSJens Scharsig #ifdef CONFIG_SYS_VCXK_DOUBLEBUFFERED
12250217deeSJens Scharsig double_bws_word = (u_short *)double_bws;
12350217deeSJens Scharsig double_bws_long = (u_long *)double_bws;
1244a1921ebSJens Scharsig (BuS Elektronik) debug("%px %px %px\n", double_bws, double_bws_word, double_bws_long);
12550217deeSJens Scharsig #endif
12650217deeSJens Scharsig display_width = width;
12750217deeSJens Scharsig display_height = height;
12850217deeSJens Scharsig #if (CONFIG_SYS_VCXK_DEFAULT_LINEALIGN == 4)
12950217deeSJens Scharsig display_bwidth = ((width + 31) / 8) & ~0x3;
13050217deeSJens Scharsig #elif (CONFIG_SYS_VCXK_DEFAULT_LINEALIGN == 2)
13150217deeSJens Scharsig display_bwidth = ((width + 15) / 8) & ~0x1;
13250217deeSJens Scharsig #else
13350217deeSJens Scharsig #error CONFIG_SYS_VCXK_DEFAULT_LINEALIGN is invalid
13450217deeSJens Scharsig #endif
135458f4381SMarek Vasut debug("linesize ((%ld + 15) / 8 & ~0x1) = %ld\n",
13650217deeSJens Scharsig display_width, display_bwidth);
13750217deeSJens Scharsig
13850217deeSJens Scharsig #ifdef CONFIG_SYS_VCXK_AUTODETECT
13950217deeSJens Scharsig VC4K16 = 0;
14050217deeSJens Scharsig vcxk_bws_long[1] = 0x0;
14150217deeSJens Scharsig vcxk_bws_long[1] = 0x55AAAA55;
14250217deeSJens Scharsig vcxk_bws_long[5] = 0x0;
14304538cdbSAnatolij Gustschin if (vcxk_bws_long[1] == 0x55AAAA55)
14404538cdbSAnatolij Gustschin VC4K16 = 1;
14550217deeSJens Scharsig #else
14650217deeSJens Scharsig VC4K16 = 1;
14750217deeSJens Scharsig debug("No autodetect: use vc4k\n");
14850217deeSJens Scharsig #endif
14950217deeSJens Scharsig
15050217deeSJens Scharsig VCXK_INIT_PIN(CONFIG_SYS_VCXK_INVERT_PORT,
15150217deeSJens Scharsig CONFIG_SYS_VCXK_INVERT_PIN, CONFIG_SYS_VCXK_INVERT_DDR, 1)
15250217deeSJens Scharsig VCXK_SET_PIN(CONFIG_SYS_VCXK_INVERT_PORT, CONFIG_SYS_VCXK_INVERT_PIN)
15350217deeSJens Scharsig
15450217deeSJens Scharsig VCXK_SET_PIN(CONFIG_SYS_VCXK_REQUEST_PORT, CONFIG_SYS_VCXK_REQUEST_PIN);
15550217deeSJens Scharsig VCXK_INIT_PIN(CONFIG_SYS_VCXK_REQUEST_PORT,
15650217deeSJens Scharsig CONFIG_SYS_VCXK_REQUEST_PIN, CONFIG_SYS_VCXK_REQUEST_DDR, 1)
15750217deeSJens Scharsig
15850217deeSJens Scharsig VCXK_INIT_PIN(CONFIG_SYS_VCXK_ACKNOWLEDGE_PORT,
15950217deeSJens Scharsig CONFIG_SYS_VCXK_ACKNOWLEDGE_PIN,
16050217deeSJens Scharsig CONFIG_SYS_VCXK_ACKNOWLEDGE_DDR, 0)
16150217deeSJens Scharsig
16250217deeSJens Scharsig VCXK_DISABLE;
16350217deeSJens Scharsig VCXK_INIT_PIN(CONFIG_SYS_VCXK_ENABLE_PORT,
16450217deeSJens Scharsig CONFIG_SYS_VCXK_ENABLE_PIN, CONFIG_SYS_VCXK_ENABLE_DDR, 1)
16550217deeSJens Scharsig
16650217deeSJens Scharsig vcxk_cls();
16750217deeSJens Scharsig vcxk_cls(); /* clear second/hidden page */
16850217deeSJens Scharsig
16950217deeSJens Scharsig vcxk_setbrightness(3, 1000);
17050217deeSJens Scharsig VCXK_ENABLE;
17150217deeSJens Scharsig return 1;
17250217deeSJens Scharsig }
17350217deeSJens Scharsig
17450217deeSJens Scharsig /*
17550217deeSJens Scharsig ****f* bus_vcxk/vcxk_setpixel
17650217deeSJens Scharsig * FUNCTION
17750217deeSJens Scharsig * set the pixel[x,y] with the given color
17850217deeSJens Scharsig * PARAMETER
17950217deeSJens Scharsig * x pixel colum
18050217deeSJens Scharsig * y pixel row
18150217deeSJens Scharsig * color <0x40 off/black
18250217deeSJens Scharsig * >0x40 on
18350217deeSJens Scharsig ***
18450217deeSJens Scharsig */
18550217deeSJens Scharsig
vcxk_setpixel(int x,int y,unsigned long color)18650217deeSJens Scharsig void vcxk_setpixel(int x, int y, unsigned long color)
18750217deeSJens Scharsig {
18850217deeSJens Scharsig vu_short dataptr;
18950217deeSJens Scharsig
19050217deeSJens Scharsig if ((x < display_width) && (y < display_height)) {
19150217deeSJens Scharsig dataptr = ((x / 16)) + (y * (display_bwidth >> 1));
19250217deeSJens Scharsig
19350217deeSJens Scharsig color = ((color >> 16) & 0xFF) |
19450217deeSJens Scharsig ((color >> 8) & 0xFF) | (color & 0xFF);
19550217deeSJens Scharsig
19650217deeSJens Scharsig if (color > 0x40) {
19750217deeSJens Scharsig VCXK_BWS_WORD_SET(dataptr, VCBITMASK(x));
19850217deeSJens Scharsig } else {
19950217deeSJens Scharsig VCXK_BWS_WORD_CLEAR(dataptr, VCBITMASK(x));
20050217deeSJens Scharsig }
20150217deeSJens Scharsig }
20250217deeSJens Scharsig }
20350217deeSJens Scharsig
20450217deeSJens Scharsig /*
20550217deeSJens Scharsig ****f* bus_vcxk/vcxk_loadimage
20650217deeSJens Scharsig * FUNCTION
20750217deeSJens Scharsig * copies a binary image to display memory
20850217deeSJens Scharsig ***
20950217deeSJens Scharsig */
21050217deeSJens Scharsig
vcxk_loadimage(ulong source)21150217deeSJens Scharsig void vcxk_loadimage(ulong source)
21250217deeSJens Scharsig {
21350217deeSJens Scharsig int cnt;
21450217deeSJens Scharsig vcxk_acknowledge_wait();
21550217deeSJens Scharsig if (VC4K16) {
21650217deeSJens Scharsig for (cnt = 0; cnt < (16384 / 4); cnt++) {
21750217deeSJens Scharsig VCXK_BWS_LONG(cnt, (*(ulong *) source));
21850217deeSJens Scharsig source = source + 4;
21950217deeSJens Scharsig }
22050217deeSJens Scharsig } else {
22150217deeSJens Scharsig for (cnt = 0; cnt < 16384; cnt++) {
22250217deeSJens Scharsig VCXK_BWS_LONG(cnt*2, (*(vu_char *) source));
22350217deeSJens Scharsig source++;
22450217deeSJens Scharsig }
22550217deeSJens Scharsig }
22650217deeSJens Scharsig vcxk_request();
22750217deeSJens Scharsig }
22850217deeSJens Scharsig
22950217deeSJens Scharsig /*
23050217deeSJens Scharsig ****f* bus_vcxk/vcxk_cls
23150217deeSJens Scharsig * FUNCTION
23250217deeSJens Scharsig * clear the display
23350217deeSJens Scharsig ***
23450217deeSJens Scharsig */
23550217deeSJens Scharsig
vcxk_cls(void)23650217deeSJens Scharsig void vcxk_cls(void)
23750217deeSJens Scharsig {
23850217deeSJens Scharsig vcxk_acknowledge_wait();
23950217deeSJens Scharsig vcxk_clear();
24050217deeSJens Scharsig vcxk_request();
24150217deeSJens Scharsig }
24250217deeSJens Scharsig
24350217deeSJens Scharsig /*
24450217deeSJens Scharsig ****f* bus_vcxk/vcxk_clear(void)
24550217deeSJens Scharsig * FUNCTION
24650217deeSJens Scharsig * clear the display memory
24750217deeSJens Scharsig ***
24850217deeSJens Scharsig */
24950217deeSJens Scharsig
vcxk_clear(void)25050217deeSJens Scharsig void vcxk_clear(void)
25150217deeSJens Scharsig {
25250217deeSJens Scharsig int cnt;
25304538cdbSAnatolij Gustschin
25450217deeSJens Scharsig for (cnt = 0; cnt < (16384 / 4); cnt++) {
25550217deeSJens Scharsig VCXK_BWS_LONG(cnt, 0)
25650217deeSJens Scharsig }
25750217deeSJens Scharsig }
25850217deeSJens Scharsig
25950217deeSJens Scharsig /*
26050217deeSJens Scharsig ****f* bus_vcxk/vcxk_setbrightness
26150217deeSJens Scharsig * FUNCTION
26250217deeSJens Scharsig * set the display brightness
26350217deeSJens Scharsig * PARAMETER
26450217deeSJens Scharsig * side 1 set front side brightness
26550217deeSJens Scharsig * 2 set back side brightness
26650217deeSJens Scharsig * 3 set brightness for both sides
26750217deeSJens Scharsig * brightness 0..1000
26850217deeSJens Scharsig ***
26950217deeSJens Scharsig */
27050217deeSJens Scharsig
vcxk_setbrightness(unsigned int side,short brightness)27150217deeSJens Scharsig void vcxk_setbrightness(unsigned int side, short brightness)
27250217deeSJens Scharsig {
27350217deeSJens Scharsig if (VC4K16) {
27450217deeSJens Scharsig if ((side == 0) || (side & 0x1))
27550217deeSJens Scharsig VC4K16_Bright1 = brightness + 23;
27650217deeSJens Scharsig if ((side == 0) || (side & 0x2))
27750217deeSJens Scharsig VC4K16_Bright2 = brightness + 23;
27850217deeSJens Scharsig } else {
27950217deeSJens Scharsig VC2K_Bright = (brightness >> 4) + 2;
28050217deeSJens Scharsig VC8K_BrightH = (brightness + 23) >> 8;
28150217deeSJens Scharsig VC8K_BrightL = (brightness + 23) & 0xFF;
28250217deeSJens Scharsig }
28350217deeSJens Scharsig }
28450217deeSJens Scharsig
28550217deeSJens Scharsig /*
28650217deeSJens Scharsig ****f* bus_vcxk/vcxk_request
28750217deeSJens Scharsig * FUNCTION
28850217deeSJens Scharsig * requests viewing of display memory
28950217deeSJens Scharsig ***
29050217deeSJens Scharsig */
29150217deeSJens Scharsig
vcxk_request(void)29250217deeSJens Scharsig int vcxk_request(void)
29350217deeSJens Scharsig {
29450217deeSJens Scharsig VCXK_CLR_PIN(CONFIG_SYS_VCXK_REQUEST_PORT,
29550217deeSJens Scharsig CONFIG_SYS_VCXK_REQUEST_PIN)
29650217deeSJens Scharsig VCXK_SET_PIN(CONFIG_SYS_VCXK_REQUEST_PORT,
29750217deeSJens Scharsig CONFIG_SYS_VCXK_REQUEST_PIN);
29850217deeSJens Scharsig return 1;
29950217deeSJens Scharsig }
30050217deeSJens Scharsig
30150217deeSJens Scharsig /*
30250217deeSJens Scharsig ****f* bus_vcxk/vcxk_acknowledge_wait
30350217deeSJens Scharsig * FUNCTION
30450217deeSJens Scharsig * wait for acknowledge viewing requests
30550217deeSJens Scharsig ***
30650217deeSJens Scharsig */
30750217deeSJens Scharsig
vcxk_acknowledge_wait(void)30850217deeSJens Scharsig int vcxk_acknowledge_wait(void)
30950217deeSJens Scharsig {
31004538cdbSAnatolij Gustschin while (VCXK_ACKNOWLEDGE)
31104538cdbSAnatolij Gustschin ;
31250217deeSJens Scharsig return 1;
31350217deeSJens Scharsig }
31450217deeSJens Scharsig
31550217deeSJens Scharsig /*
31650217deeSJens Scharsig ****f* bus_vcxk/vcxk_draw_mono
31750217deeSJens Scharsig * FUNCTION
31850217deeSJens Scharsig * copies a monochrom bitmap (BMP-Format) from given memory
31950217deeSJens Scharsig * PARAMETER
32050217deeSJens Scharsig * dataptr pointer to bitmap
32150217deeSJens Scharsig * x output bitmap @ columne
32250217deeSJens Scharsig * y output bitmap @ row
32350217deeSJens Scharsig ***
32450217deeSJens Scharsig */
32550217deeSJens Scharsig
vcxk_draw_mono(unsigned char * dataptr,unsigned long linewidth,unsigned long cp_width,unsigned long cp_height)32650217deeSJens Scharsig void vcxk_draw_mono(unsigned char *dataptr, unsigned long linewidth,
32750217deeSJens Scharsig unsigned long cp_width, unsigned long cp_height)
32850217deeSJens Scharsig {
32950217deeSJens Scharsig unsigned char *lineptr;
33050217deeSJens Scharsig unsigned long xcnt, ycnt;
33150217deeSJens Scharsig
33250217deeSJens Scharsig for (ycnt = cp_height; ycnt > 0; ycnt--) {
33350217deeSJens Scharsig lineptr = dataptr;
33450217deeSJens Scharsig for (xcnt = 0; xcnt < cp_width; xcnt++) {
33550217deeSJens Scharsig if ((*lineptr << (xcnt % 8)) & 0x80)
33650217deeSJens Scharsig vcxk_setpixel(xcnt, ycnt - 1, 0xFFFFFF);
33750217deeSJens Scharsig else
33850217deeSJens Scharsig vcxk_setpixel(xcnt, ycnt-1, 0);
33950217deeSJens Scharsig
34004538cdbSAnatolij Gustschin if ((xcnt % 8) == 7)
34104538cdbSAnatolij Gustschin lineptr++;
34250217deeSJens Scharsig } /* endfor xcnt */
34350217deeSJens Scharsig dataptr = dataptr + linewidth;
34450217deeSJens Scharsig } /* endfor ycnt */
34550217deeSJens Scharsig }
34650217deeSJens Scharsig
34750217deeSJens Scharsig /*
34850217deeSJens Scharsig ****f* bus_vcxk/vcxk_display_bitmap
34950217deeSJens Scharsig * FUNCTION
35050217deeSJens Scharsig * copies a bitmap (BMP-Format) to the given position
35150217deeSJens Scharsig * PARAMETER
35250217deeSJens Scharsig * addr pointer to bitmap
35350217deeSJens Scharsig * x output bitmap @ columne
35450217deeSJens Scharsig * y output bitmap @ row
35550217deeSJens Scharsig ***
35650217deeSJens Scharsig */
35750217deeSJens Scharsig
vcxk_display_bitmap(ulong addr,int x,int y)35850217deeSJens Scharsig int vcxk_display_bitmap(ulong addr, int x, int y)
35950217deeSJens Scharsig {
3601c3dbe56SSimon Glass struct bmp_image *bmp;
36150217deeSJens Scharsig unsigned long width;
36250217deeSJens Scharsig unsigned long height;
36350217deeSJens Scharsig unsigned long bpp;
36450217deeSJens Scharsig
36550217deeSJens Scharsig unsigned long lw;
36650217deeSJens Scharsig
36750217deeSJens Scharsig unsigned long c_width;
36850217deeSJens Scharsig unsigned long c_height;
36950217deeSJens Scharsig unsigned char *dataptr;
37050217deeSJens Scharsig
3711c3dbe56SSimon Glass bmp = (struct bmp_image *)addr;
37250217deeSJens Scharsig if ((bmp->header.signature[0] == 'B') &&
37350217deeSJens Scharsig (bmp->header.signature[1] == 'M')) {
37450217deeSJens Scharsig width = le32_to_cpu(bmp->header.width);
37550217deeSJens Scharsig height = le32_to_cpu(bmp->header.height);
37650217deeSJens Scharsig bpp = le16_to_cpu(bmp->header.bit_count);
37750217deeSJens Scharsig
37850217deeSJens Scharsig dataptr = (unsigned char *) bmp +
37950217deeSJens Scharsig le32_to_cpu(bmp->header.data_offset);
38050217deeSJens Scharsig
38150217deeSJens Scharsig if (display_width < (width + x))
38250217deeSJens Scharsig c_width = display_width - x;
38350217deeSJens Scharsig else
38450217deeSJens Scharsig c_width = width;
38550217deeSJens Scharsig if (display_height < (height + y))
38650217deeSJens Scharsig c_height = display_height - y;
38750217deeSJens Scharsig else
38850217deeSJens Scharsig c_height = height;
38950217deeSJens Scharsig
39050217deeSJens Scharsig lw = (((width + 7) / 8) + 3) & ~0x3;
39150217deeSJens Scharsig
39250217deeSJens Scharsig if (c_height < height)
39350217deeSJens Scharsig dataptr = dataptr + lw * (height - c_height);
39450217deeSJens Scharsig switch (bpp) {
39550217deeSJens Scharsig case 1:
39650217deeSJens Scharsig vcxk_draw_mono(dataptr, lw, c_width, c_height);
39750217deeSJens Scharsig break;
39850217deeSJens Scharsig default:
39950217deeSJens Scharsig printf("Error: %ld bit per pixel "
40050217deeSJens Scharsig "not supported by VCxK\n", bpp);
40150217deeSJens Scharsig return 0;
40250217deeSJens Scharsig }
40350217deeSJens Scharsig } else {
40450217deeSJens Scharsig printf("Error: no valid bmp at %lx\n", (ulong) bmp);
40550217deeSJens Scharsig return 0;
40650217deeSJens Scharsig }
40750217deeSJens Scharsig return 1;
40850217deeSJens Scharsig }
40950217deeSJens Scharsig
41050217deeSJens Scharsig /*
41150217deeSJens Scharsig ****f* bus_vcxk/video_display_bitmap
41250217deeSJens Scharsig ***
41350217deeSJens Scharsig */
41450217deeSJens Scharsig
video_display_bitmap(ulong addr,int x,int y)41550217deeSJens Scharsig int video_display_bitmap(ulong addr, int x, int y)
41650217deeSJens Scharsig {
41750217deeSJens Scharsig vcxk_acknowledge_wait();
41850217deeSJens Scharsig if (vcxk_display_bitmap(addr, x, y)) {
41950217deeSJens Scharsig vcxk_request();
42050217deeSJens Scharsig return 0;
42150217deeSJens Scharsig }
42250217deeSJens Scharsig return 1;
42350217deeSJens Scharsig }
42450217deeSJens Scharsig
42550217deeSJens Scharsig /* EOF */
426