19a57b7d2SSøren Schmidt /*- 29a57b7d2SSøren Schmidt * Copyright (c) 1991-1997 S�ren Schmidt 39a57b7d2SSøren Schmidt * All rights reserved. 49a57b7d2SSøren Schmidt * 59a57b7d2SSøren Schmidt * Redistribution and use in source and binary forms, with or without 69a57b7d2SSøren Schmidt * modification, are permitted provided that the following conditions 79a57b7d2SSøren Schmidt * are met: 89a57b7d2SSøren Schmidt * 1. Redistributions of source code must retain the above copyright 99a57b7d2SSøren Schmidt * notice, this list of conditions and the following disclaimer, 109a57b7d2SSøren Schmidt * in this position and unchanged. 119a57b7d2SSøren Schmidt * 2. Redistributions in binary form must reproduce the above copyright 129a57b7d2SSøren Schmidt * notice, this list of conditions and the following disclaimer in the 139a57b7d2SSøren Schmidt * documentation and/or other materials provided with the distribution. 149a57b7d2SSøren Schmidt * 3. The name of the author may not be used to endorse or promote products 159a57b7d2SSøren Schmidt * derived from this software withough specific prior written permission. 169a57b7d2SSøren Schmidt * 179a57b7d2SSøren Schmidt * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR 189a57b7d2SSøren Schmidt * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES 199a57b7d2SSøren Schmidt * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. 209a57b7d2SSøren Schmidt * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, 219a57b7d2SSøren Schmidt * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT 229a57b7d2SSøren Schmidt * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 239a57b7d2SSøren Schmidt * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 249a57b7d2SSøren Schmidt * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 259a57b7d2SSøren Schmidt * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF 269a57b7d2SSøren Schmidt * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 279a57b7d2SSøren Schmidt * 285e7a62b2SKazutaka YOKOTA * $Id: bitmap.c,v 1.1 1997/08/17 21:09:34 sos Exp $ 299a57b7d2SSøren Schmidt */ 309a57b7d2SSøren Schmidt 319a57b7d2SSøren Schmidt #include <sys/types.h> 329a57b7d2SSøren Schmidt #include <signal.h> 339a57b7d2SSøren Schmidt #include "vgl.h" 349a57b7d2SSøren Schmidt 359a57b7d2SSøren Schmidt static byte VGLPlane[4][128]; 369a57b7d2SSøren Schmidt static byte mask[8] = {0xff, 0x7f, 0x3f, 0x1f, 0x0f, 0x07, 0x03, 0x01}; 379a57b7d2SSøren Schmidt static int color2bit[16] = {0x00000000, 0x00000001, 0x00000100, 0x00000101, 389a57b7d2SSøren Schmidt 0x00010000, 0x00010001, 0x00010100, 0x00010101, 399a57b7d2SSøren Schmidt 0x01000000, 0x01000001, 0x01000100, 0x01000101, 409a57b7d2SSøren Schmidt 0x01010000, 0x01010001, 0x01010100, 0x01010101}; 419a57b7d2SSøren Schmidt 429a57b7d2SSøren Schmidt static void 439a57b7d2SSøren Schmidt WriteVerticalLine(VGLBitmap *dst, int x, int y, int width, byte *line) 449a57b7d2SSøren Schmidt { 459a57b7d2SSøren Schmidt int i, pos, last, planepos, start_offset, end_offset, offset; 469a57b7d2SSøren Schmidt unsigned int word = 0; 479a57b7d2SSøren Schmidt byte *address; 489a57b7d2SSøren Schmidt 499a57b7d2SSøren Schmidt switch (dst->Type) { 509a57b7d2SSøren Schmidt case VIDBUF4: 519a57b7d2SSøren Schmidt address = dst->Bitmap + (dst->Xsize/8 * y) + x/8; 529a57b7d2SSøren Schmidt start_offset = (x & 0x07); 539a57b7d2SSøren Schmidt end_offset = (x + width) & 0x07; 549a57b7d2SSøren Schmidt offset = start_offset; 559a57b7d2SSøren Schmidt pos = 0; 569a57b7d2SSøren Schmidt planepos = 0; 579a57b7d2SSøren Schmidt while (pos < width) { 589a57b7d2SSøren Schmidt word = 0; 599a57b7d2SSøren Schmidt last = pos + 8 - offset; 609a57b7d2SSøren Schmidt while (pos < last && pos < width) 619a57b7d2SSøren Schmidt word = (word<<1) | color2bit[line[pos++]&0x0f]; 629a57b7d2SSøren Schmidt VGLPlane[0][planepos] = word; 639a57b7d2SSøren Schmidt VGLPlane[1][planepos] = word>>8; 649a57b7d2SSøren Schmidt VGLPlane[2][planepos] = word>>16; 659a57b7d2SSøren Schmidt VGLPlane[3][planepos] = word>>24; 669a57b7d2SSøren Schmidt planepos++; 679a57b7d2SSøren Schmidt offset = 0; 689a57b7d2SSøren Schmidt } 699a57b7d2SSøren Schmidt planepos--; 709a57b7d2SSøren Schmidt if (end_offset) { 719a57b7d2SSøren Schmidt word <<= (8 - end_offset); 729a57b7d2SSøren Schmidt VGLPlane[0][planepos] = word; 739a57b7d2SSøren Schmidt VGLPlane[1][planepos] = word>>8; 749a57b7d2SSøren Schmidt VGLPlane[2][planepos] = word>>16; 759a57b7d2SSøren Schmidt VGLPlane[3][planepos] = word>>24; 769a57b7d2SSøren Schmidt } 779a57b7d2SSøren Schmidt if (start_offset || end_offset) 789a57b7d2SSøren Schmidt width+=8; 799a57b7d2SSøren Schmidt for (i=0; i<4; i++) { 809a57b7d2SSøren Schmidt outb(0x3c4, 0x02); 819a57b7d2SSøren Schmidt outb(0x3c5, 0x01<<i); 829a57b7d2SSøren Schmidt outb(0x3ce, 0x04); 839a57b7d2SSøren Schmidt outb(0x3cf, i); 849a57b7d2SSøren Schmidt if (start_offset) 859a57b7d2SSøren Schmidt VGLPlane[i][0] |= *address & ~mask[start_offset]; 869a57b7d2SSøren Schmidt if (end_offset) 879a57b7d2SSøren Schmidt VGLPlane[i][planepos] |= *(address + planepos) & mask[end_offset]; 889a57b7d2SSøren Schmidt bcopy(&VGLPlane[i][0], address, width/8); 899a57b7d2SSøren Schmidt } 909a57b7d2SSøren Schmidt break; 919a57b7d2SSøren Schmidt case VIDBUF8X: 925e7a62b2SKazutaka YOKOTA address = dst->Bitmap + (dst->Xsize/2 * y) + x/4; 939a57b7d2SSøren Schmidt for (i=0; i<4; i++) { 949a57b7d2SSøren Schmidt outb(0x3c4, 0x02); 955e7a62b2SKazutaka YOKOTA outb(0x3c5, 0x01 << ((x + i)%4)); 965e7a62b2SKazutaka YOKOTA for (planepos=0, pos=i; pos<width; planepos++, pos+=4) 979a57b7d2SSøren Schmidt address[planepos] = line[pos]; 985e7a62b2SKazutaka YOKOTA if ((x + i)%4 == 3) 995e7a62b2SKazutaka YOKOTA ++address; 1009a57b7d2SSøren Schmidt } 1019a57b7d2SSøren Schmidt break; 1029a57b7d2SSøren Schmidt case VIDBUF8: 1039a57b7d2SSøren Schmidt case MEMBUF: 1049a57b7d2SSøren Schmidt address = dst->Bitmap + (dst->Xsize * y) + x; 1059a57b7d2SSøren Schmidt bcopy(line, address, width); 1069a57b7d2SSøren Schmidt break; 1079a57b7d2SSøren Schmidt 1089a57b7d2SSøren Schmidt default: 1099a57b7d2SSøren Schmidt } 1109a57b7d2SSøren Schmidt } 1119a57b7d2SSøren Schmidt 1129a57b7d2SSøren Schmidt static void 1139a57b7d2SSøren Schmidt ReadVerticalLine(VGLBitmap *src, int x, int y, int width, byte *line) 1149a57b7d2SSøren Schmidt { 1159a57b7d2SSøren Schmidt int i, bit, pos, count, planepos, start_offset, end_offset, offset; 1169a57b7d2SSøren Schmidt byte *address; 1179a57b7d2SSøren Schmidt 1189a57b7d2SSøren Schmidt switch (src->Type) { 1199a57b7d2SSøren Schmidt case VIDBUF4: 1209a57b7d2SSøren Schmidt address = src->Bitmap + (src->Xsize/8 * y) + x/8; 1219a57b7d2SSøren Schmidt start_offset = (x & 0x07); 1229a57b7d2SSøren Schmidt end_offset = (x + width) & 0x07; 1239a57b7d2SSøren Schmidt offset = start_offset; 1249a57b7d2SSøren Schmidt if (start_offset) 1259a57b7d2SSøren Schmidt count = (width - (8 - start_offset)) / 8 + 1; 1269a57b7d2SSøren Schmidt else 1279a57b7d2SSøren Schmidt count = width / 8; 1289a57b7d2SSøren Schmidt if (end_offset) 1299a57b7d2SSøren Schmidt count++; 1309a57b7d2SSøren Schmidt for (i=0; i<4; i++) { 1319a57b7d2SSøren Schmidt outb(0x3ce, 0x04); 1329a57b7d2SSøren Schmidt outb(0x3cf, i); 1339a57b7d2SSøren Schmidt bcopy(address, &VGLPlane[i][0], count); 1349a57b7d2SSøren Schmidt } 1359a57b7d2SSøren Schmidt pos = 0; 1369a57b7d2SSøren Schmidt planepos = 0; 1379a57b7d2SSøren Schmidt while (pos < width) { 1389a57b7d2SSøren Schmidt for (bit = (7-offset); bit >= 0 && pos < width; bit--, pos++) { 1399a57b7d2SSøren Schmidt line[pos] = (VGLPlane[0][planepos] & (1<<bit) ? 1 : 0) | 1409a57b7d2SSøren Schmidt ((VGLPlane[1][planepos] & (1<<bit) ? 1 : 0) << 1) | 1419a57b7d2SSøren Schmidt ((VGLPlane[2][planepos] & (1<<bit) ? 1 : 0) << 2) | 1429a57b7d2SSøren Schmidt ((VGLPlane[3][planepos] & (1<<bit) ? 1 : 0) << 3); 1439a57b7d2SSøren Schmidt } 1449a57b7d2SSøren Schmidt planepos++; 1459a57b7d2SSøren Schmidt offset = 0; 1469a57b7d2SSøren Schmidt } 1479a57b7d2SSøren Schmidt break; 1489a57b7d2SSøren Schmidt case VIDBUF8X: 1495e7a62b2SKazutaka YOKOTA address = src->Bitmap + (src->Xsize/2 * y) + x/4; 1509a57b7d2SSøren Schmidt for (i=0; i<4; i++) { 1519a57b7d2SSøren Schmidt outb(0x3ce, 0x04); 1525e7a62b2SKazutaka YOKOTA outb(0x3cf, (x + i)%4); 1535e7a62b2SKazutaka YOKOTA for (planepos=0, pos=i; pos<width; planepos++, pos+=4) 1549a57b7d2SSøren Schmidt line[pos] = address[planepos]; 1555e7a62b2SKazutaka YOKOTA if ((x + i)%4 == 3) 1565e7a62b2SKazutaka YOKOTA ++address; 1579a57b7d2SSøren Schmidt } 1589a57b7d2SSøren Schmidt break; 1599a57b7d2SSøren Schmidt case VIDBUF8: 1609a57b7d2SSøren Schmidt case MEMBUF: 1619a57b7d2SSøren Schmidt address = src->Bitmap + (src->Xsize * y) + x; 1629a57b7d2SSøren Schmidt bcopy(address, line, width); 1639a57b7d2SSøren Schmidt break; 1649a57b7d2SSøren Schmidt default: 1659a57b7d2SSøren Schmidt } 1669a57b7d2SSøren Schmidt } 1679a57b7d2SSøren Schmidt 1689a57b7d2SSøren Schmidt int 1699a57b7d2SSøren Schmidt __VGLBitmapCopy(VGLBitmap *src, int srcx, int srcy, 1709a57b7d2SSøren Schmidt VGLBitmap *dst, int dstx, int dsty, int width, int hight) 1719a57b7d2SSøren Schmidt { 1729a57b7d2SSøren Schmidt int srcline, dstline; 1739a57b7d2SSøren Schmidt 1745e7a62b2SKazutaka YOKOTA if (srcx>src->Xsize||srcy>src->Ysize||dstx>dst->Xsize||dsty>dst->Ysize) 1759a57b7d2SSøren Schmidt return -1; 1769a57b7d2SSøren Schmidt if (srcx < 0) { 1779a57b7d2SSøren Schmidt width=width+srcx; dstx-=srcx; srcx=0; 1789a57b7d2SSøren Schmidt } 1799a57b7d2SSøren Schmidt if (srcy < 0) { 1809a57b7d2SSøren Schmidt hight=hight+srcy; dsty-=srcy; srcy=0; 1819a57b7d2SSøren Schmidt } 1829a57b7d2SSøren Schmidt if (dstx < 0) { 1839a57b7d2SSøren Schmidt width=width+dstx; srcx-=dstx; dstx=0; 1849a57b7d2SSøren Schmidt } 1859a57b7d2SSøren Schmidt if (dsty < 0) { 1869a57b7d2SSøren Schmidt hight=hight+dsty; srcy-=dsty; dsty=0; 1879a57b7d2SSøren Schmidt } 1889a57b7d2SSøren Schmidt if (srcx+width > src->Xsize) 1899a57b7d2SSøren Schmidt width=src->Xsize-srcx; 1909a57b7d2SSøren Schmidt if (srcy+hight > src->Ysize) 1919a57b7d2SSøren Schmidt hight=src->Ysize-srcy; 1929a57b7d2SSøren Schmidt if (dstx+width > dst->Xsize) 1939a57b7d2SSøren Schmidt width=dst->Xsize-dstx; 1949a57b7d2SSøren Schmidt if (dsty+hight > dst->Ysize) 1959a57b7d2SSøren Schmidt hight=dst->Ysize-dsty; 1969a57b7d2SSøren Schmidt if (width < 0 || hight < 0) 1979a57b7d2SSøren Schmidt return -1; 1989a57b7d2SSøren Schmidt if (src->Type == MEMBUF) { 1999a57b7d2SSøren Schmidt for (srcline=srcy, dstline=dsty; srcline<srcy+hight; srcline++, dstline++) { 2009a57b7d2SSøren Schmidt WriteVerticalLine(dst, dstx, dstline, width, 2019a57b7d2SSøren Schmidt (src->Bitmap+(srcline*src->Xsize)+srcx)); 2029a57b7d2SSøren Schmidt } 2039a57b7d2SSøren Schmidt } 2049a57b7d2SSøren Schmidt else if (dst->Type == MEMBUF) { 2059a57b7d2SSøren Schmidt for (srcline=srcy, dstline=dsty; srcline<srcy+hight; srcline++, dstline++) { 2069a57b7d2SSøren Schmidt ReadVerticalLine(src, srcx, srcline, width, 2079a57b7d2SSøren Schmidt (dst->Bitmap+(dstline*dst->Xsize)+dstx)); 2089a57b7d2SSøren Schmidt } 2099a57b7d2SSøren Schmidt } 2109a57b7d2SSøren Schmidt else { 2119a57b7d2SSøren Schmidt byte buffer[1024]; 2129a57b7d2SSøren Schmidt for (srcline=srcy, dstline=dsty; srcline<srcy+hight; srcline++, dstline++) { 2139a57b7d2SSøren Schmidt ReadVerticalLine(src, srcx, srcline, width, buffer); 2149a57b7d2SSøren Schmidt WriteVerticalLine(dst, dstx, dstline, width, buffer); 2159a57b7d2SSøren Schmidt } 2169a57b7d2SSøren Schmidt } 2179a57b7d2SSøren Schmidt return 0; 2189a57b7d2SSøren Schmidt } 2199a57b7d2SSøren Schmidt 2209a57b7d2SSøren Schmidt int 2219a57b7d2SSøren Schmidt VGLBitmapCopy(VGLBitmap *src, int srcx, int srcy, 2229a57b7d2SSøren Schmidt VGLBitmap *dst, int dstx, int dsty, int width, int hight) 2239a57b7d2SSøren Schmidt { 2249a57b7d2SSøren Schmidt int error; 2259a57b7d2SSøren Schmidt 2269a57b7d2SSøren Schmidt VGLMouseFreeze(dstx, dsty, width, hight, 0); 2279a57b7d2SSøren Schmidt error = __VGLBitmapCopy(src, srcx, srcy, dst, dstx, dsty, width, hight); 2289a57b7d2SSøren Schmidt VGLMouseUnFreeze(); 2299a57b7d2SSøren Schmidt return error; 2309a57b7d2SSøren Schmidt } 2319a57b7d2SSøren Schmidt 232