1 /* 2 * Copyright 2006-2009, Axel Dörfler, axeld@pinc-software.de. 3 * Distributed under the terms of the MIT License. 4 */ 5 6 7 #include "vga.h" 8 #include "driver.h" 9 10 #include <vga.h> 11 12 #include <KernelExport.h> 13 14 15 status_t 16 vga_set_indexed_colors(uint8 first, uint8 *colors, uint16 count) 17 { 18 if (first + count > 256) 19 count = 256 - first; 20 21 gISA->write_io_8(VGA_COLOR_WRITE_MODE, first); 22 23 // write VGA palette 24 for (int32 i = first; i < count; i++) { 25 uint8 color[3]; 26 if (user_memcpy(color, &colors[i * 3], 3) < B_OK) 27 return B_BAD_ADDRESS; 28 29 // VGA (usually) has only 6 bits per gun 30 gISA->write_io_8(VGA_COLOR_DATA, color[0] >> 2); 31 gISA->write_io_8(VGA_COLOR_DATA, color[1] >> 2); 32 gISA->write_io_8(VGA_COLOR_DATA, color[2] >> 2); 33 } 34 return B_OK; 35 } 36 37 38 status_t 39 vga_planar_blit(vesa_shared_info *info, uint8 *src, int32 srcBPR, 40 int32 left, int32 top, int32 right, int32 bottom) 41 { 42 int32 dstBPR = info->bytes_per_row; 43 uint8 *dst = info->frame_buffer + top * dstBPR + left / 8; 44 45 // TODO: this is awfully slow... 46 // TODO: assumes BGR order 47 for (int32 y = top; y <= bottom; y++) { 48 for (int32 plane = 0; plane < 4; plane++) { 49 // select the plane we intend to write to and read from 50 gISA->write_io_16(VGA_SEQUENCER_INDEX, (1 << (plane + 8)) | 0x02); 51 gISA->write_io_16(VGA_GRAPHICS_INDEX, (plane << 8) | 0x04); 52 53 uint8* srcHandle = src; 54 uint8* dstHandle = dst; 55 uint8 current8 = dstHandle[0]; 56 // we store 8 pixels before writing them back 57 58 int32 x = left; 59 for (; x <= right; x++) { 60 uint8 rgba[4]; 61 if (user_memcpy(rgba, srcHandle, 4) < B_OK) 62 return B_BAD_ADDRESS; 63 uint8 pixel = (308 * rgba[2] + 600 * rgba[1] 64 + 116 * rgba[0]) / 16384; 65 srcHandle += 4; 66 67 if (pixel & (1 << plane)) 68 current8 |= 0x80 >> (x & 7); 69 else 70 current8 &= ~(0x80 >> (x & 7)); 71 72 if ((x & 7) == 7) { 73 // last pixel in 8 pixel group 74 dstHandle[0] = current8; 75 dstHandle++; 76 current8 = dstHandle[0]; 77 } 78 } 79 80 if (x & 7) { 81 // last pixel has not been written yet 82 dstHandle[0] = current8; 83 } 84 } 85 dst += dstBPR; 86 src += srcBPR; 87 } 88 return B_OK; 89 } 90 91