//video.c // 08/13/03 Josh Holtrop // Modified: 11/12/03 //Initialized the video mode information block video_mode and allocated double-buffer memory for graphics display void video_init(ModeInfoBlock *mib) { video_mode = *mib; //Get a buffer region in memory for double-buffering video memory in 32bpp vid_Buffer = mm_palloc((4*video_mode.XResolution*video_mode.YResolution)/4096+1, PID_KERNEL); if ((dword)vid_Buffer == 0) { printf("ERROR - COULD NOT ALLOCATE MEMORY FOR VIDEO DOUBLE-BUFFER!!\n"); halt(); } dword tot = ((video_mode.XResolution) * (video_mode.YResolution)); int a; for (a = 0; a < tot; a++) { if (a < (tot / 4)) vid_Buffer[a] = 0x00FF0000; else if (a < (tot / 2)) vid_Buffer[a] = 0x0000FF00; else if (a < ((tot * 3) / 4)) vid_Buffer[a] = 0x000000FF; else vid_Buffer[a] = 0x00FFFFFF; } int VXR = video_mode.XResolution; int VYR = video_mode.YResolution; video_rectf(VXR*3/11, 0, VXR*4/11, VYR-1, 0x00000088); //test rectangles, draws "HOS" video_rectf(VXR*7/11, 0, VXR*8/11, VYR-1, 0x00000088); video_rectf(VXR/11, 0, VXR*2/11, VYR*2/5, 0x00000088); video_rectf(VXR/11, VYR*3/5, VXR*2/11, VYR-1, 0x00000088); video_rectf(VXR*5/11, VYR/5, VXR*6/11, VYR*4/5, 0x00000088); video_rectf(VXR*9/11, VYR/5, VXR-1, VYR*2/5, 0x00000088); video_rectf(VXR*8/11, VYR*3/5, VXR*10/11, VYR*4/5, 0x00000088); int b; for (a = 0; a < 256; a++) { for (b = 0; b < 256; b++) { video_pset(a+5, b+30, (a<<16)|(b<<8)); video_pset(a+270, b+30, (a<<8)|(b)); video_pset(a+535, b+30, (a<<16)|(b)); video_pset(a+5, b+290, (a<<16)|(b<<8)|0x000000ff); video_pset(a+270, b+290, (a<<8)|(b)|0x00ff0000); video_pset(a+535, b+290, (a<<16)|(b)|0x0000ff00); } } int fx; int fy = 25; int fc; int fr; for (fr = 0; fr < 16; fr++) { fx = 15; for (fc = 0; fc < 16; fc++) { video_renderChar(fx, fy, fr*16+fc, 0xFFFFFF); fx += 8; } fy += 10; } video_copyBuffer(); } //Renders a character using stdfont[] as a bitmask void video_renderChar(int x, int y, int character, dword color) { int charpos = (character & 0xFF) * 8; int row; int col; for (row = 0; row < 8; row++) { for (col = 0; col < 5; col++) { if ((stdfont[charpos+row] >> (col+3)) & 0x01) video_pset(x+(5-col), y+row, color); } } } //Draws a horizontal line void video_horiz(int y, int x1, int x2, dword color) { if (x1 > x2) { int tmp = x2; x2 = x1; x1 = tmp; //x2 >= x1 now } if (x2 < 0) return; if (x1 > video_mode.XResolution) return; if (x1 < 0) x1 = 0; if (x2 > video_mode.XResolution) x2 = video_mode.XResolution; int pixel = y*video_mode.XResolution+x1; for (; x1 <= x2; x1++) { vid_Buffer[pixel++] = color; } } //Draws a vertical line void video_vert(int x, int y1, int y2, dword color) { if (y1 > y2) { int tmp = y2; y2 = y1; y1 = tmp; //y2 >= y1 now } if (y2 < 0) return; if (y1 > video_mode.YResolution) return; if (y1 < 0) y1 = 0; if (y2 > video_mode.YResolution) y2 = video_mode.YResolution; int pixel = y1*video_mode.XResolution+x; for (; y1 <= y2; y1++) { vid_Buffer[pixel] = color; pixel+=video_mode.XResolution; } } //Draws a rectangle void video_rect(int x1, int y1, int x2, int y2, dword color) { video_horiz(y1, x1, x2, color); video_horiz(y2, x1, x2, color); video_vert(x1, y1, y2, color); video_vert(x2, y1, y2, color); } //Draws a filled rectangle void video_rectf(int x1, int y1, int x2, int y2, dword color) { if (y2 < y1) { int tmp = y2; y2 = y1; y1 = tmp; } for (; y1 <= y2; y1++) video_horiz(y1, x1, x2, color); } //Draws a single pixel inline void video_pset(int x, int y, dword color) { if ((x < 0) || (x > video_mode.XResolution) || (y < 0) || (y > video_mode.YResolution)) return; vid_Buffer[y*video_mode.XResolution+x] = color; } //Copies double-buffer to VESA Linear Frame Buffer void video_copyBuffer() { switch (video_mode.BitsPerPixel) { case 32: video_copyBuffer32((dword)vid_Buffer, video_mode.PhysBasePtr, video_mode.XResolution*video_mode.YResolution); break; case 24: video_copyBuffer24((dword)vid_Buffer, video_mode.PhysBasePtr, video_mode.XResolution*video_mode.YResolution); break; case 16: video_copyBuffer16((dword)vid_Buffer, video_mode.PhysBasePtr, video_mode.XResolution*video_mode.YResolution); break; } /*int pixel; dword color; for (pixel = 0; pixel < video_mode.XResolution*video_mode.YResolution; pixel++) { switch(video_mode.BitsPerPixel) { case 16: color = vid_Buffer[pixel]; ((word *)video_mode.PhysBasePtr)[pixel] = ((color&0xFF)>>3) | ((((color>>8)&0xFF)>>2)<<5) | ((((color>>16)&0xFF)>>3)<<11); //vid_ptr16[pixel] = ((color&0xFF)>>3) | ((((color>>8)&0xFF)>>3)<<5) | ((((color>>16)&0xFF)>>3)<<10); //15 bit mode? break; case 24: color = vid_Buffer[pixel]; ((byte *)video_mode.PhysBasePtr)[pixel*3] = color & 0xFF; ((byte *)video_mode.PhysBasePtr)[pixel*3+1] = (color>>8) & 0xFF; ((byte *)video_mode.PhysBasePtr)[pixel*3+2] = (color>>16) & 0xFF; break; case 32: color = vid_Buffer[pixel]; ((dword *)video_mode.PhysBasePtr)[pixel] = color; } } */ }