/[cebix]/SheepShaver/src/Unix/video_x.cpp
ViewVC logotype

Diff of /SheepShaver/src/Unix/video_x.cpp

Parent Directory Parent Directory | Revision Log Revision Log | View Patch Patch

revision 1.21 by gbeauche, Mon May 10 16:42:37 2004 UTC revision 1.32 by gbeauche, Fri Jul 2 06:06:34 2004 UTC
# Line 46  Line 46 
46  #include "about_window.h"  #include "about_window.h"
47  #include "video.h"  #include "video.h"
48  #include "video_defs.h"  #include "video_defs.h"
49    #include "video_blit.h"
50    
51  #define DEBUG 0  #define DEBUG 0
52  #include "debug.h"  #include "debug.h"
# Line 57  using std::sort; Line 58  using std::sort;
58    
59  // Constants  // Constants
60  const char KEYCODE_FILE_NAME[] = DATADIR "/keycodes";  const char KEYCODE_FILE_NAME[] = DATADIR "/keycodes";
61  static const bool mac_cursor_enabled = false;   // Flag: Enable MacOS to X11 copy of cursor?  static const bool hw_mac_cursor_accl = true;    // Flag: Enable MacOS to X11 copy of cursor?
62    
63  // Global variables  // Global variables
64  static int32 frame_skip;  static int32 frame_skip;
# Line 65  static int16 mouse_wheel_mode; Line 66  static int16 mouse_wheel_mode;
66  static int16 mouse_wheel_lines;  static int16 mouse_wheel_lines;
67  static bool redraw_thread_active = false;       // Flag: Redraw thread installed  static bool redraw_thread_active = false;       // Flag: Redraw thread installed
68  static pthread_attr_t redraw_thread_attr;       // Redraw thread attributes  static pthread_attr_t redraw_thread_attr;       // Redraw thread attributes
69    static volatile bool redraw_thread_cancel;      // Flag: Cancel Redraw thread
70  static pthread_t redraw_thread;                         // Redraw thread  static pthread_t redraw_thread;                         // Redraw thread
71    
72  static bool local_X11;                                          // Flag: X server running on local machine?  static bool local_X11;                                          // Flag: X server running on local machine?
# Line 82  static const bool use_vosf = false; // Line 84  static const bool use_vosf = false; //
84    
85  static bool palette_changed = false;            // Flag: Palette changed, redraw thread must update palette  static bool palette_changed = false;            // Flag: Palette changed, redraw thread must update palette
86  static bool ctrl_down = false;                          // Flag: Ctrl key pressed  static bool ctrl_down = false;                          // Flag: Ctrl key pressed
87    static bool caps_on = false;                            // Flag: Caps Lock on
88  static bool quit_full_screen = false;           // Flag: DGA close requested from redraw thread  static bool quit_full_screen = false;           // Flag: DGA close requested from redraw thread
89  static volatile bool quit_full_screen_ack = false;      // Acknowledge for quit_full_screen  static volatile bool quit_full_screen_ack = false;      // Acknowledge for quit_full_screen
90  static bool emerg_quit = false;                         // Flag: Ctrl-Esc pressed, emergency quit requested from MacOS thread  static bool emerg_quit = false;                         // Flag: Ctrl-Esc pressed, emergency quit requested from MacOS thread
# Line 99  static int depth; // Depth of Mac Line 102  static int depth; // Depth of Mac
102  static Window rootwin, the_win;                         // Root window and our window  static Window rootwin, the_win;                         // Root window and our window
103  static int num_depths = 0;                                      // Number of available X depths  static int num_depths = 0;                                      // Number of available X depths
104  static int *avail_depths = NULL;                        // List of available X depths  static int *avail_depths = NULL;                        // List of available X depths
105    static VisualFormat visualFormat;
106  static XVisualInfo visualInfo;  static XVisualInfo visualInfo;
107  static Visual *vis;  static Visual *vis;
108  static int color_class;  static int color_class;
# Line 506  static bool open_window(int width, int h Line 510  static bool open_window(int width, int h
510          XSetState(x_display, the_gc, black_pixel, white_pixel, GXcopy, AllPlanes);          XSetState(x_display, the_gc, black_pixel, white_pixel, GXcopy, AllPlanes);
511    
512          // Create cursor          // Create cursor
513          if (mac_cursor_enabled) {          if (hw_mac_cursor_accl) {
514                  cursor_image = XCreateImage(x_display, vis, 1, XYPixmap, 0, (char *)MacCursor + 4, 16, 16, 16, 2);                  cursor_image = XCreateImage(x_display, vis, 1, XYPixmap, 0, (char *)MacCursor + 4, 16, 16, 16, 2);
515                  cursor_image->byte_order = MSBFirst;                  cursor_image->byte_order = MSBFirst;
516                  cursor_image->bitmap_bit_order = MSBFirst;                  cursor_image->bitmap_bit_order = MSBFirst;
# Line 538  static bool open_window(int width, int h Line 542  static bool open_window(int width, int h
542          native_byte_order = (XImageByteOrder(x_display) == LSBFirst);          native_byte_order = (XImageByteOrder(x_display) == LSBFirst);
543  #endif  #endif
544  #ifdef ENABLE_VOSF  #ifdef ENABLE_VOSF
545          Screen_blitter_init(&visualInfo, native_byte_order, depth);          Screen_blitter_init(visualFormat, native_byte_order, depth);
546  #endif  #endif
547    
548          // Set bytes per row          // Set bytes per row
# Line 612  static bool open_dga(int width, int heig Line 616  static bool open_dga(int width, int heig
616  #if REAL_ADDRESSING || DIRECT_ADDRESSING  #if REAL_ADDRESSING || DIRECT_ADDRESSING
617          // Screen_blitter_init() returns TRUE if VOSF is mandatory          // Screen_blitter_init() returns TRUE if VOSF is mandatory
618          // i.e. the framebuffer update function is not Blit_Copy_Raw          // i.e. the framebuffer update function is not Blit_Copy_Raw
619          use_vosf = Screen_blitter_init(&visualInfo, native_byte_order, depth);          use_vosf = Screen_blitter_init(visualFormat, native_byte_order, depth);
620    
621          if (use_vosf) {          if (use_vosf) {
622            // Allocate memory for frame buffer (SIZE is extended to page-boundary)            // Allocate memory for frame buffer (SIZE is extended to page-boundary)
# Line 649  static bool open_display(void) Line 653  static bool open_display(void)
653                  return false;                  return false;
654          }          }
655    
656            // Build up visualFormat structure
657            visualFormat.depth = visualInfo.depth;
658            visualFormat.Rmask = visualInfo.red_mask;
659            visualFormat.Gmask = visualInfo.green_mask;
660            visualFormat.Bmask = visualInfo.blue_mask;
661    
662          // Create color maps          // Create color maps
663          if (color_class == PseudoColor || color_class == DirectColor) {          if (color_class == PseudoColor || color_class == DirectColor) {
664                  cmap[0] = XCreateColormap(x_display, rootwin, vis, AllocAll);                  cmap[0] = XCreateColormap(x_display, rootwin, vis, AllocAll);
# Line 882  static void keycode_init(void) Line 892  static void keycode_init(void)
892    
893                  // Search for server vendor string, then read keycodes                  // Search for server vendor string, then read keycodes
894                  const char *vendor = ServerVendor(x_display);                  const char *vendor = ServerVendor(x_display);
895    #if (defined(__APPLE__) && defined(__MACH__))
896                    // Force use of MacX mappings on MacOS X with Apple's X server
897                    int dummy;
898                    if (XQueryExtension(x_display, "Apple-DRI", &dummy, &dummy, &dummy))
899                            vendor = "MacX";
900    #endif
901                  bool vendor_found = false;                  bool vendor_found = false;
902                  char line[256];                  char line[256];
903                  while (fgets(line, 255, f)) {                  while (fgets(line, 255, f)) {
# Line 1161  bool VideoInit(void) Line 1177  bool VideoInit(void)
1177                  if (apple_id != -1)                  if (apple_id != -1)
1178                          cur_mode = find_mode(default_mode, apple_id, DIS_SCREEN);                          cur_mode = find_mode(default_mode, apple_id, DIS_SCREEN);
1179          }          }
1180          if (cur_mode == -1)          if (cur_mode == -1) {
1181                  cur_mode = find_mode(default_mode, APPLE_W_640x480, DIS_WINDOW);                  // pick up first windowed mode available
1182                    for (VideoInfo *p = VModes; p->viType != DIS_INVALID; p++) {
1183                            if (p->viType == DIS_WINDOW && p->viAppleMode == default_mode) {
1184                                    cur_mode = p - VModes;
1185                                    break;
1186                            }
1187                    }
1188            }
1189          assert(cur_mode != -1);          assert(cur_mode != -1);
1190    
1191  #if DEBUG  #if DEBUG
# Line 1185  bool VideoInit(void) Line 1208  bool VideoInit(void)
1208          // Start periodic thread          // Start periodic thread
1209          XSync(x_display, false);          XSync(x_display, false);
1210          Set_pthread_attr(&redraw_thread_attr, 0);          Set_pthread_attr(&redraw_thread_attr, 0);
1211            redraw_thread_cancel = false;
1212          redraw_thread_active = (pthread_create(&redraw_thread, &redraw_thread_attr, redraw_func, NULL) == 0);          redraw_thread_active = (pthread_create(&redraw_thread, &redraw_thread_attr, redraw_func, NULL) == 0);
1213          D(bug("Redraw thread installed (%ld)\n", redraw_thread));          D(bug("Redraw thread installed (%ld)\n", redraw_thread));
1214          return true;          return true;
# Line 1199  void VideoExit(void) Line 1223  void VideoExit(void)
1223  {  {
1224          // Stop redraw thread          // Stop redraw thread
1225          if (redraw_thread_active) {          if (redraw_thread_active) {
1226                    redraw_thread_cancel = true;
1227                  pthread_cancel(redraw_thread);                  pthread_cancel(redraw_thread);
1228                  pthread_join(redraw_thread, NULL);                  pthread_join(redraw_thread, NULL);
1229                  redraw_thread_active = false;                  redraw_thread_active = false;
# Line 1477  static int kc_decode(KeySym ks) Line 1502  static int kc_decode(KeySym ks)
1502          return -1;          return -1;
1503  }  }
1504    
1505  static int event2keycode(XKeyEvent &ev)  static int event2keycode(XKeyEvent &ev, bool key_down)
1506  {  {
1507          KeySym ks;          KeySym ks;
         int as;  
1508          int i = 0;          int i = 0;
1509    
1510          do {          do {
1511                  ks = XLookupKeysym(&ev, i++);                  ks = XLookupKeysym(&ev, i++);
1512                  as = kc_decode(ks);                  int as = kc_decode(ks);
1513                  if (as != -1)                  if (as >= 0)
1514                            return as;
1515                    if (as == -2)
1516                          return as;                          return as;
1517          } while (ks != NoSymbol);          } while (ks != NoSymbol);
1518    
# Line 1561  static void handle_events(void) Line 1587  static void handle_events(void)
1587    
1588                          // Keyboard                          // Keyboard
1589                          case KeyPress: {                          case KeyPress: {
1590                                  int code = event2keycode(event.xkey);                                  int code = -1;
1591                                  if (use_keycodes && code != -1)                                  if (use_keycodes) {
1592                                            if (event2keycode(event.xkey, true) != -2)      // This is called to process the hotkeys
1593                                          code = keycode_table[event.xkey.keycode & 0xff];                                          code = keycode_table[event.xkey.keycode & 0xff];
1594                                  if (code != -1) {                                  } else
1595                                            code = event2keycode(event.xkey, true);
1596                                    if (code >= 0) {
1597                                          if (!emul_suspended) {                                          if (!emul_suspended) {
1598                                                    if (code == 0x39) {     // Caps Lock pressed
1599                                                            if (caps_on) {
1600                                                                    ADBKeyUp(code);
1601                                                                    caps_on = false;
1602                                                            } else {
1603                                                                    ADBKeyDown(code);
1604                                                                    caps_on = true;
1605                                                            }
1606                                                    } else
1607                                                  ADBKeyDown(code);                                                  ADBKeyDown(code);
1608                                                  if (code == 0x36)                                                  if (code == 0x36)
1609                                                          ctrl_down = true;                                                          ctrl_down = true;
# Line 1577  static void handle_events(void) Line 1615  static void handle_events(void)
1615                                  break;                                  break;
1616                          }                          }
1617                          case KeyRelease: {                          case KeyRelease: {
1618                                  int code = event2keycode(event.xkey);                                  int code = -1;
1619                                  if (use_keycodes && code != 1)                                  if (use_keycodes) {
1620                                            if (event2keycode(event.xkey, false) != -2)     // This is called to process the hotkeys
1621                                          code = keycode_table[event.xkey.keycode & 0xff];                                          code = keycode_table[event.xkey.keycode & 0xff];
1622                                  if (code != -1) {                                  } else
1623                                            code = event2keycode(event.xkey, false);
1624                                    if (code >= 0 && code != 0x39) {        // Don't propagate Caps Lock releases
1625                                          ADBKeyUp(code);                                          ADBKeyUp(code);
1626                                          if (code == 0x36)                                          if (code == 0x36)
1627                                                  ctrl_down = false;                                                  ctrl_down = false;
# Line 1620  void VideoVBL(void) Line 1661  void VideoVBL(void)
1661    
1662    
1663  /*  /*
  *  Install graphics acceleration  
  */  
   
 // Rectangle inversion  
 template< int bpp >  
 static inline void do_invrect(uint8 *dest, uint32 length)  
 {  
 #define INVERT_1(PTR, OFS) ((uint8  *)(PTR))[OFS] = ~((uint8  *)(PTR))[OFS]  
 #define INVERT_2(PTR, OFS) ((uint16 *)(PTR))[OFS] = ~((uint16 *)(PTR))[OFS]  
 #define INVERT_4(PTR, OFS) ((uint32 *)(PTR))[OFS] = ~((uint32 *)(PTR))[OFS]  
 #define INVERT_8(PTR, OFS) ((uint64 *)(PTR))[OFS] = ~((uint64 *)(PTR))[OFS]  
   
 #ifndef UNALIGNED_PROFITABLE  
         // Align on 16-bit boundaries  
         if (bpp < 16 && (((uintptr)dest) & 1)) {  
                 INVERT_1(dest, 0);  
                 dest += 1; length -= 1;  
         }  
   
         // Align on 32-bit boundaries  
         if (bpp < 32 && (((uintptr)dest) & 2)) {  
                 INVERT_2(dest, 0);  
                 dest += 2; length -= 2;  
         }  
 #endif  
   
         // Invert 8-byte words  
         if (length >= 8) {  
                 const int r = (length / 8) % 8;  
                 dest += r * 8;  
   
                 int n = ((length / 8) + 7) / 8;  
                 switch (r) {  
                 case 0: do {  
                                 dest += 64;  
                                 INVERT_8(dest, -8);  
                 case 7: INVERT_8(dest, -7);  
                 case 6: INVERT_8(dest, -6);  
                 case 5: INVERT_8(dest, -5);  
                 case 4: INVERT_8(dest, -4);  
                 case 3: INVERT_8(dest, -3);  
                 case 2: INVERT_8(dest, -2);  
                 case 1: INVERT_8(dest, -1);  
                                 } while (--n > 0);  
                 }  
         }  
   
         // 32-bit cell to invert?  
         if (length & 4) {  
                 INVERT_4(dest, 0);  
                 if (bpp <= 16)  
                         dest += 4;  
         }  
   
         // 16-bit cell to invert?  
         if (bpp <= 16 && (length & 2)) {  
                 INVERT_2(dest, 0);  
                 if (bpp <= 8)  
                         dest += 2;  
         }  
   
         // 8-bit cell to invert?  
         if (bpp <= 8 && (length & 1))  
                 INVERT_1(dest, 0);  
   
 #undef INVERT_1  
 #undef INVERT_2  
 #undef INVERT_4  
 #undef INVERT_8  
 }  
   
 void NQD_invrect(uint32 p)  
 {  
         D(bug("accl_invrect %08x\n", p));  
   
         // Get inversion parameters  
         int16 dest_X = (int16)ReadMacInt16(p + acclDestRect + 2) - (int16)ReadMacInt16(p + acclDestBoundsRect + 2);  
         int16 dest_Y = (int16)ReadMacInt16(p + acclDestRect + 0) - (int16)ReadMacInt16(p + acclDestBoundsRect + 0);  
         int16 width  = (int16)ReadMacInt16(p + acclDestRect + 6) - (int16)ReadMacInt16(p + acclDestRect + 2);  
         int16 height = (int16)ReadMacInt16(p + acclDestRect + 4) - (int16)ReadMacInt16(p + acclDestRect + 0);  
         D(bug(" dest X %d, dest Y %d\n", dest_X, dest_Y));  
         D(bug(" width %d, height %d, bytes_per_row %d\n", width, height, (int32)ReadMacInt32(p + acclDestRowBytes)));  
   
         //!!?? pen_mode == 14  
   
         // And perform the inversion  
         const int bpp = bytes_per_pixel(ReadMacInt32(p + acclDestPixelSize));  
         const int dest_row_bytes = (int32)ReadMacInt32(p + acclDestRowBytes);  
         uint8 *dest = Mac2HostAddr(ReadMacInt32(p + acclDestBaseAddr) + (dest_Y * dest_row_bytes) + (dest_X * bpp));  
         width *= bpp;  
         switch (bpp) {  
         case 1:  
                 for (int i = 0; i < height; i++) {  
                         do_invrect<8>(dest, width);  
                         dest += dest_row_bytes;  
                 }  
                 break;  
         case 2:  
                 for (int i = 0; i < height; i++) {  
                         do_invrect<16>(dest, width);  
                         dest += dest_row_bytes;  
                 }  
                 break;  
         case 4:  
                 for (int i = 0; i < height; i++) {  
                         do_invrect<32>(dest, width);  
                         dest += dest_row_bytes;  
                 }  
                 break;  
         }  
 }  
   
 // Rectangle filling  
 template< int bpp >  
 static inline void do_fillrect(uint8 *dest, uint32 color, uint32 length)  
 {  
 #define FILL_1(PTR, OFS, VAL) ((uint8  *)(PTR))[OFS] = (VAL)  
 #define FILL_2(PTR, OFS, VAL) ((uint16 *)(PTR))[OFS] = (VAL)  
 #define FILL_4(PTR, OFS, VAL) ((uint32 *)(PTR))[OFS] = (VAL)  
 #define FILL_8(PTR, OFS, VAL) ((uint64 *)(PTR))[OFS] = (VAL)  
   
 #ifndef UNALIGNED_PROFITABLE  
         // Align on 16-bit boundaries  
         if (bpp < 16 && (((uintptr)dest) & 1)) {  
                 FILL_1(dest, 0, color);  
                 dest += 1; length -= 1;  
         }  
   
         // Align on 32-bit boundaries  
         if (bpp < 32 && (((uintptr)dest) & 2)) {  
                 FILL_2(dest, 0, color);  
                 dest += 2; length -= 2;  
         }  
 #endif  
   
         // Fill 8-byte words  
         if (length >= 8) {  
                 const uint64 c = (((uint64)color) << 32) | color;  
                 const int r = (length / 8) % 8;  
                 dest += r * 8;  
   
                 int n = ((length / 8) + 7) / 8;  
                 switch (r) {  
                 case 0: do {  
                                 dest += 64;  
                                 FILL_8(dest, -8, c);  
                 case 7: FILL_8(dest, -7, c);  
                 case 6: FILL_8(dest, -6, c);  
                 case 5: FILL_8(dest, -5, c);  
                 case 4: FILL_8(dest, -4, c);  
                 case 3: FILL_8(dest, -3, c);  
                 case 2: FILL_8(dest, -2, c);  
                 case 1: FILL_8(dest, -1, c);  
                                 } while (--n > 0);  
                 }  
         }  
   
         // 32-bit cell to fill?  
         if (length & 4) {  
                 FILL_4(dest, 0, color);  
                 if (bpp <= 16)  
                         dest += 4;  
         }  
   
         // 16-bit cell to fill?  
         if (bpp <= 16 && (length & 2)) {  
                 FILL_2(dest, 0, color);  
                 if (bpp <= 8)  
                         dest += 2;  
         }  
   
         // 8-bit cell to fill?  
         if (bpp <= 8 && (length & 1))  
                 FILL_1(dest, 0, color);  
   
 #undef FILL_1  
 #undef FILL_2  
 #undef FILL_4  
 #undef FILL_8  
 }  
   
 void NQD_fillrect(uint32 p)  
 {  
         D(bug("accl_fillrect %08x\n", p));  
   
         // Get filling parameters  
         int16 dest_X = (int16)ReadMacInt16(p + acclDestRect + 2) - (int16)ReadMacInt16(p + acclDestBoundsRect + 2);  
         int16 dest_Y = (int16)ReadMacInt16(p + acclDestRect + 0) - (int16)ReadMacInt16(p + acclDestBoundsRect + 0);  
         int16 width  = (int16)ReadMacInt16(p + acclDestRect + 6) - (int16)ReadMacInt16(p + acclDestRect + 2);  
         int16 height = (int16)ReadMacInt16(p + acclDestRect + 4) - (int16)ReadMacInt16(p + acclDestRect + 0);  
         uint32 color = ReadMacInt32(p + acclPenMode) == 8 ? ReadMacInt32(p + acclForePen) : ReadMacInt32(p + acclBackPen);  
         D(bug(" dest X %d, dest Y %d\n", dest_X, dest_Y));  
         D(bug(" width %d, height %d\n", width, height));  
         D(bug(" bytes_per_row %d color %08x\n", (int32)ReadMacInt32(p + acclDestRowBytes), color));  
   
         // And perform the fill  
         const int bpp = bytes_per_pixel(ReadMacInt32(p + acclDestPixelSize));  
         const int dest_row_bytes = (int32)ReadMacInt32(p + acclDestRowBytes);  
         uint8 *dest = Mac2HostAddr(ReadMacInt32(p + acclDestBaseAddr) + (dest_Y * dest_row_bytes) + (dest_X * bpp));  
         width *= bpp;  
         switch (bpp) {  
         case 1:  
                 for (int i = 0; i < height; i++) {  
                         memset(dest, color, width);  
                         dest += dest_row_bytes;  
                 }  
                 break;  
         case 2:  
                 for (int i = 0; i < height; i++) {  
                         do_fillrect<16>(dest, color, width);  
                         dest += dest_row_bytes;  
                 }  
                 break;  
         case 4:  
                 for (int i = 0; i < height; i++) {  
                         do_fillrect<32>(dest, color, width);  
                         dest += dest_row_bytes;  
                 }  
                 break;  
         }  
 }  
   
 bool NQD_fillrect_hook(uint32 p)  
 {  
         D(bug("accl_fillrect_hook %08x\n", p));  
   
         // Check if we can accelerate this fillrect  
         if (ReadMacInt32(p + 0x284) != 0 && ReadMacInt32(p + acclDestPixelSize) >= 8) {  
                 const int transfer_mode = ReadMacInt32(p + acclTransferMode);  
                 if (transfer_mode == 8) {  
                         // Fill  
                         WriteMacInt32(p + acclDrawProc, NativeTVECT(NATIVE_FILLRECT));  
                         return true;  
                 }  
                 else if (transfer_mode == 10) {  
                         // Invert  
                         WriteMacInt32(p + acclDrawProc, NativeTVECT(NATIVE_INVRECT));  
                         return true;  
                 }  
         }  
         return false;  
 }  
   
 // Rectangle blitting  
 // TODO: optimize for VOSF and target pixmap == screen  
 void NQD_bitblt(uint32 p)  
 {  
         D(bug("accl_bitblt %08x\n", p));  
   
         // Get blitting parameters  
         int16 src_X  = (int16)ReadMacInt16(p + acclSrcRect + 2) - (int16)ReadMacInt16(p + acclSrcBoundsRect + 2);  
         int16 src_Y  = (int16)ReadMacInt16(p + acclSrcRect + 0) - (int16)ReadMacInt16(p + acclSrcBoundsRect + 0);  
         int16 dest_X = (int16)ReadMacInt16(p + acclDestRect + 2) - (int16)ReadMacInt16(p + acclDestBoundsRect + 2);  
         int16 dest_Y = (int16)ReadMacInt16(p + acclDestRect + 0) - (int16)ReadMacInt16(p + acclDestBoundsRect + 0);  
         int16 width  = (int16)ReadMacInt16(p + acclDestRect + 6) - (int16)ReadMacInt16(p + acclDestRect + 2);  
         int16 height = (int16)ReadMacInt16(p + acclDestRect + 4) - (int16)ReadMacInt16(p + acclDestRect + 0);  
         D(bug(" src addr %08x, dest addr %08x\n", ReadMacInt32(p + acclSrcBaseAddr), ReadMacInt32(p + acclDestBaseAddr)));  
         D(bug(" src X %d, src Y %d, dest X %d, dest Y %d\n", src_X, src_Y, dest_X, dest_Y));  
         D(bug(" width %d, height %d\n", width, height));  
   
         // And perform the blit  
         const int bpp = bytes_per_pixel(ReadMacInt32(p + acclSrcPixelSize));  
         width *= bpp;  
         if ((int32)ReadMacInt32(p + acclSrcRowBytes) > 0) {  
                 const int src_row_bytes = (int32)ReadMacInt32(p + acclSrcRowBytes);  
                 const int dst_row_bytes = (int32)ReadMacInt32(p + acclDestRowBytes);  
                 uint8 *src = Mac2HostAddr(ReadMacInt32(p + acclSrcBaseAddr) + (src_Y * src_row_bytes) + (src_X * bpp));  
                 uint8 *dst = Mac2HostAddr(ReadMacInt32(p + acclDestBaseAddr) + (dest_Y * dst_row_bytes) + (dest_X * bpp));  
                 for (int i = 0; i < height; i++) {  
                         memcpy(dst, src, width);  
                         src += src_row_bytes;  
                         dst += dst_row_bytes;  
                 }  
         }  
         else {  
                 const int src_row_bytes = -(int32)ReadMacInt32(p + acclSrcRowBytes);  
                 const int dst_row_bytes = -(int32)ReadMacInt32(p + acclDestRowBytes);  
                 uint8 *src = Mac2HostAddr(ReadMacInt32(p + acclSrcBaseAddr) + ((src_Y + height - 1) * src_row_bytes) + (src_X * bpp));  
                 uint8 *dst = Mac2HostAddr(ReadMacInt32(p + acclDestBaseAddr) + ((dest_Y + height - 1) * dst_row_bytes) + (dest_X * bpp));  
                 for (int i = height - 1; i >= 0; i--) {  
                         memcpy(dst, src, width);  
                         src -= src_row_bytes;  
                         dst -= dst_row_bytes;  
                 }  
         }  
 }  
   
 /*  
   BitBlt transfer modes:  
   0 : srcCopy  
   1 : srcOr  
   2 : srcXor  
   3 : srcBic  
   4 : notSrcCopy  
   5 : notSrcOr  
   6 : notSrcXor  
   7 : notSrcBic  
   32 : blend  
   33 : addPin  
   34 : addOver  
   35 : subPin  
   36 : transparent  
   37 : adMax  
   38 : subOver  
   39 : adMin  
   50 : hilite  
 */  
   
 bool NQD_bitblt_hook(uint32 p)  
 {  
         D(bug("accl_draw_hook %08x\n", p));  
   
         // Check if we can accelerate this bitblt  
         if (ReadMacInt32(p + 0x018) + ReadMacInt32(p + 0x128) == 0 &&  
                 ReadMacInt32(p + 0x130) == 0 &&  
                 ReadMacInt32(p + acclSrcPixelSize) >= 8 &&  
                 ReadMacInt32(p + acclSrcPixelSize) == ReadMacInt32(p + acclDestPixelSize) &&  
                 (ReadMacInt32(p + acclSrcRowBytes) ^ ReadMacInt32(p + acclDestRowBytes)) >= 0 && // same sign?  
                 ReadMacInt32(p + acclTransferMode) == 0 &&                                                                               // srcCopy?  
                 ReadMacInt32(p + 0x15c) > 0) {  
   
                 // Yes, set function pointer  
                 WriteMacInt32(p + acclDrawProc, NativeTVECT(NATIVE_BITBLT));  
                 return true;  
         }  
         return false;  
 }  
   
 // Wait for graphics operation to finish  
 bool NQD_sync_hook(uint32 arg)  
 {  
         D(bug("accl_sync_hook %08x\n", arg));  
         return true;  
 }  
   
 void VideoInstallAccel(void)  
 {  
         // Temporary hack until it's fixed for e.g. little-endian & 64-bit platforms  
 #ifndef __powerpc__  
         return;  
 #endif  
   
         // Install acceleration hooks  
         if (PrefsFindBool("gfxaccel")) {  
                 D(bug("Video: Installing acceleration hooks\n"));  
                 uint32 base;  
   
                 SheepVar bitblt_hook_info(sizeof(accl_hook_info));  
                 base = bitblt_hook_info.addr();  
                 WriteMacInt32(base + 0, NativeTVECT(NATIVE_BITBLT_HOOK));  
                 WriteMacInt32(base + 4, NativeTVECT(NATIVE_SYNC_HOOK));  
                 WriteMacInt32(base + 8, ACCL_BITBLT);  
                 NQDMisc(6, bitblt_hook_info.ptr());  
   
                 SheepVar fillrect_hook_info(sizeof(accl_hook_info));  
                 base = fillrect_hook_info.addr();  
                 WriteMacInt32(base + 0, NativeTVECT(NATIVE_FILLRECT_HOOK));  
                 WriteMacInt32(base + 4, NativeTVECT(NATIVE_SYNC_HOOK));  
                 WriteMacInt32(base + 8, ACCL_FILLRECT);  
                 NQDMisc(6, fillrect_hook_info.ptr());  
         }  
 }  
   
   
 /*  
1664   *  Change video mode   *  Change video mode
1665   */   */
1666    
# Line 2092  void video_set_palette(void) Line 1768  void video_set_palette(void)
1768    
1769  bool video_can_change_cursor(void)  bool video_can_change_cursor(void)
1770  {  {
1771          return mac_cursor_enabled && (display_type != DIS_SCREEN);          return hw_mac_cursor_accl && (display_type != DIS_SCREEN);
1772  }  }
1773    
1774    
# Line 2276  static void *redraw_func(void *arg) Line 1952  static void *redraw_func(void *arg)
1952          int64 ticks = 0;          int64 ticks = 0;
1953          uint64 next = GetTicks_usec() + VIDEO_REFRESH_DELAY;          uint64 next = GetTicks_usec() + VIDEO_REFRESH_DELAY;
1954    
1955          for (;;) {          while (!redraw_thread_cancel) {
1956    
1957                  // Pause if requested (during video mode switches)                  // Pause if requested (during video mode switches)
1958                  while (thread_stop_req)                  while (thread_stop_req)
# Line 2341  static void *redraw_func(void *arg) Line 2017  static void *redraw_func(void *arg)
2017                                                  update_display();                                                  update_display();
2018    
2019                                          // Set new cursor image if it was changed                                          // Set new cursor image if it was changed
2020                                          if (mac_cursor_enabled && cursor_changed) {                                          if (hw_mac_cursor_accl && cursor_changed) {
2021                                                  cursor_changed = false;                                                  cursor_changed = false;
2022                                                  memcpy(cursor_image->data, MacCursor + 4, 32);                                                  uint8 *x_data = (uint8 *)cursor_image->data;
2023                                                  memcpy(cursor_mask_image->data, MacCursor + 36, 32);                                                  uint8 *x_mask = (uint8 *)cursor_mask_image->data;
2024                                                    for (int i = 0; i < 32; i++) {
2025                                                            x_mask[i] = MacCursor[4 + i] | MacCursor[36 + i];
2026                                                            x_data[i] = MacCursor[4 + i];
2027                                                    }
2028                                                  XDisplayLock();                                                  XDisplayLock();
2029                                                  XFreeCursor(x_display, mac_cursor);                                                  XFreeCursor(x_display, mac_cursor);
2030                                                  XPutImage(x_display, cursor_map, cursor_gc, cursor_image, 0, 0, 0, 0, 16, 16);                                                  XPutImage(x_display, cursor_map, cursor_gc, cursor_image, 0, 0, 0, 0, 16, 16);

Legend:
Removed from v.1.21  
changed lines
  Added in v.1.32

Christian Bauer">Christian Bauer
ViewVC Help
Powered by ViewVC 1.1.15