Annotation of uae/mac.c, revision 1.1.1.1

1.1       root        1:  /* 
                      2:   * UAE - The Un*x Amiga Emulator
                      3:   * 
                      4:   * Mac port specific stuff
                      5:   * 
                      6:   * (c) 1996 Ernesto Corvi
                      7:   */
                      8: 
                      9: #include <stdio.h>
                     10: #include <stdlib.h>
                     11: #include <string.h>
                     12: #include <QDOffscreen.h>
                     13: #include <Palettes.h>
                     14: #include <Profiler.h>
                     15: 
                     16: #include "mackbd.h"
                     17: #include "config.h"
                     18: #include "amiga.h"
                     19: #include "options.h"
                     20: #include "memory.h"
                     21: #include "custom.h"
                     22: #include "newcpu.h"
                     23: #include "xwin.h"
                     24: #include "keyboard.h"
                     25: #include "keybuf.h"
                     26: 
                     27: #define kQuitError 128
                     28: 
                     29: extern bool left, right, top, bot, but;
                     30: 
                     31: KeyMap keys,keysold;
                     32: GDHandle               curDevice;
                     33: int            oldDepth=0;
                     34: static int screen;
                     35: Boolean        RM=false,Joy=false;
                     36: WindowPtr mywin;
                     37: short  gOldMBarHeight;
                     38: RgnHandle gMBarRgn;
                     39: static int bitdepth;
                     40: KeyMap theKeys;
                     41: 
                     42: unsigned long refresh;
                     43: char *xlinebuffer;
                     44: unsigned int *obuff;
                     45: long int xcolors[4096];
                     46: 
                     47:  /* Keyboard and mouse */
                     48: 
                     49: static bool keystate[256];
                     50: 
                     51: bool buttonstate[3];
                     52: int lastmx, lastmy;
                     53: bool newmousecounters;
                     54: static bool inwindow;
                     55: 
                     56: int GetRawCode (long set0, long set1, long set2, long set3);
                     57: 
                     58: static inline unsigned long doMask(int p, int bits, int shift)
                     59: {
                     60:     /* p is a value from 0 to 15 (Amiga color value)
                     61:      * scale to 0..255, shift to align msb with mask, and apply mask */
                     62: 
                     63:     unsigned long val = p * 0x11111111UL;
                     64:     val >>= (32 - bits);
                     65:     val <<= shift;
                     66: 
                     67:     return val;
                     68: }
                     69: 
                     70: static void InitXColors(void)
                     71: {
                     72:     int n=16;
                     73:     int red_bits = 5;
                     74:     int green_bits = 5;
                     75:     int blue_bits = 5;
                     76:     int red_shift = 10;
                     77:     int green_shift = 5;
                     78:     int blue_shift = 0;
                     79:     int i=0;
                     80:     int r,g,b;
                     81:        
                     82:     for(i = 0; i < 4096; i++) {
                     83:        r = i >> 8;
                     84:        g = (i >> 4) & 0xF;
                     85:        b = i & 0xF;
                     86:        xcolors[i] = (doMask(r, red_bits, red_shift) 
                     87:                      | doMask(g, green_bits, green_shift) 
                     88:                      | doMask(b, blue_bits, blue_shift));
                     89:     }
                     90: }
                     91: 
                     92: static void InitToolbox(void)
                     93: {
                     94:        InitGraf (&qd.thePort);
                     95:        InitFonts ();
                     96:        FlushEvents (everyEvent,0);
                     97:        InitWindows ();
                     98:        InitMenus ();
                     99:        TEInit ();
                    100:        InitDialogs (nil);
                    101:        InitCursor ();
                    102: }
                    103: 
                    104: static void HideMenuBar(void)
                    105: {
                    106:     Rect mBarRect;
                    107: 
                    108:     /* GET RID OF THE MENU BAR */
                    109:                                        
                    110:     gOldMBarHeight = GetMBarHeight();
                    111:     /* make the Menu Bar's height zero */
                    112:     LMSetMBarHeight(0);
                    113:     SetRect(&mBarRect, qd.screenBits.bounds.left, qd.screenBits.bounds.top,
                    114:            qd.screenBits.bounds.right, qd.screenBits.bounds.top + gOldMBarHeight);
                    115:     gMBarRgn = NewRgn();
                    116:     RectRgn(gMBarRgn, &mBarRect);
                    117:     UnionRgn(LMGetGrayRgn(), gMBarRgn, LMGetGrayRgn());        /* tell the desktop it covers the menu bar */
                    118: 
                    119:     PaintOne(nil, gMBarRgn); /* redraw desktop */
                    120: }
                    121: 
                    122: static void ShowMenuBar(void)
                    123: {
                    124:     LMSetMBarHeight(gOldMBarHeight); /* make the menu bar's height normal */
                    125:     DiffRgn(LMGetGrayRgn(), gMBarRgn, LMGetGrayRgn()); /* remove the menu bar from the desktop */
                    126:     DisposeRgn(gMBarRgn);
                    127: }
                    128: 
                    129: void graphics_init()
                    130: {      int i;
                    131:        long p1;
                    132:        long tmp;
                    133: 
                    134:     Rect       windowRectangle={0,0,480,640};
                    135:     InitToolbox();
                    136:        
                    137:        if (CheckForSetup()) ExitToShell();
                    138:        
                    139:        HideMenuBar();
                    140:        mywin = NewCWindow(nil, &windowRectangle, "\pUAE", true, 2, (WindowPtr)-1L, false, 0);
                    141:     SetPort(mywin);
                    142: 
                    143:     PaintRect(&qd.screenBits.bounds);
                    144:     
                    145:     xlinebuffer = (char *)malloc (3200);
                    146:     InitXColors();
                    147:     buttonstate[0] = buttonstate[1] = buttonstate[2] = false;
                    148:     for(i=0; i<256; i++) keystate[i] = false;
                    149:     
                    150:     lastmx = lastmy = 0; newmousecounters = false; inwindow = false;
                    151:     
                    152:     obuff=(unsigned int *)NewPtrClear(481*1280);
                    153:        {
                    154:                for(p1=0;p1 < (480*1280);p1++)
                    155:                        *obuff=-1;
                    156:        }
                    157:        
                    158:        HideCursor();
                    159:     refresh=TickCount();
                    160:     
                    161: /*    tmp=ProfilerInit(collectDetailed,bestTimeBase,200,10); */
                    162: }
                    163: 
                    164: void graphics_leave()
                    165: {
                    166: /*     ProfilerDump((unsigned char *)"\pmyProf");
                    167:        ProfilerTerm();
                    168:  */
                    169:     DisposeWindow(mywin);
                    170:     ShowCursor();
                    171:     if (oldDepth != 0) SetDepth(curDevice,oldDepth,0,0);
                    172:     ShowMenuBar();
                    173:     FlushEvents (everyEvent,0);
                    174:     ExitToShell();
                    175: }
                    176: 
                    177: static bool next_line_double;
                    178: static int next_line_pos = 0;
                    179: 
                    180: void flush_screen ()
                    181: {  
                    182:     GrafPtr oldPort;
                    183:     short      y,x,daColor=0;
                    184:     RGBColor   daColorRGB;
                    185:     unsigned char *winbaseaddr;
                    186:     double *src,*dest;
                    187:     unsigned long winrowbytes;
                    188:     PixMapHandle       ph;
                    189:     
                    190:     if (TickCount() < refresh + 4) return;
                    191:     GetPort(&oldPort);
                    192:     SetPort(mywin);
                    193:    
                    194:     ph=GetGWorldPixMap((CGrafPort *) mywin);
                    195:     LockPixels(ph);
                    196:     winbaseaddr=( unsigned char *) GetPixBaseAddr(ph);
                    197:     winrowbytes=(*ph)->rowBytes & 0x3FFF;
                    198:     winbaseaddr-=((**ph).bounds.left);
                    199:     winbaseaddr-=((**ph).bounds.top*winrowbytes);
                    200:     dest=(double *)winbaseaddr;
                    201:     src=(double *)obuff;
                    202:     
                    203:     for (y=1; y< 480; y++)
                    204:     {
                    205:        for (x=0;x < 160;x++)
                    206:        {  
                    207:            *dest++ = *src++;
                    208:        }
                    209:        dest=(double *)(winbaseaddr+(y*winrowbytes));
                    210:     }
                    211:     UnlockPixels(ph);
                    212:     SetPort(oldPort);
                    213: 
                    214: }
                    215: 
                    216: void prepare_line (int y, bool need_double)
                    217: {
                    218:     next_line_double = need_double;
                    219:     next_line_pos = y;
                    220: }
                    221: 
                    222: void flush_line()
                    223: {
                    224:     short i;
                    225:     char *dst,*src;
                    226:     double *dst1,*src1;
                    227:         
                    228:     if ((next_line_pos < 508) && (next_line_pos > 28))
                    229:     {  
                    230:        dst=(char *)obuff+((next_line_pos-28)*1280);
                    231:        src=(char *)xlinebuffer+292;
                    232:        BlockMove(src,dst,1280);  
                    233:     }
                    234:     if (next_line_double)
                    235:     {  
                    236:        if ((next_line_pos+1 < 508) && (next_line_pos+1 > 28))
                    237:        {       
                    238:            dst1=(double *)obuff+((next_line_pos+1-28)*160);
                    239:            src1=(double *)obuff+((next_line_pos-28)*160);
                    240:            for (i=0;i < 160;i++)
                    241:            {  
                    242:                *dst1++=*src1++;
                    243:            }
                    244:        }
                    245:     }
                    246: }
                    247: 
                    248: /* Decode KeySyms. This function knows about all keys that are common 
                    249:  * between different keyboard languages.
                    250:  */
                    251: static int kc_decode (long ks)
                    252: {      
                    253:     switch (ks)
                    254:     {
                    255:      case kAKeyMap: return AK_A;
                    256:      case kBKeyMap: return AK_B;
                    257:      case kCKeyMap: return AK_C;
                    258:      case kDKeyMap: return AK_D;
                    259:      case kEKeyMap: return AK_E;
                    260:      case kFKeyMap: return AK_F;
                    261:      case kGKeyMap: return AK_G;
                    262:      case kHKeyMap: return AK_H;
                    263:      case kIKeyMap: return AK_I;
                    264:      case kJKeyMap: return AK_J;
                    265:      case kKKeyMap: return AK_K;
                    266:      case kLKeyMap: return AK_L;
                    267:      case kMKeyMap: return AK_M;
                    268:      case kNKeyMap: return AK_N;
                    269:      case kOKeyMap: return AK_O;
                    270:      case kPKeyMap: return AK_P;
                    271:      case kQKeyMap: return AK_Q;
                    272:      case kRKeyMap: return AK_R;
                    273:      case kSKeyMap: return AK_S;
                    274:      case kTKeyMap: return AK_T;
                    275:      case kUKeyMap: return AK_U;
                    276:      case kVKeyMap: return AK_V;
                    277:      case kWKeyMap: return AK_W;
                    278:      case kXKeyMap: return AK_X;
                    279:      
                    280:      case k0KeyMap: return AK_0;
                    281:      case k1KeyMap: return AK_1;
                    282:      case k2KeyMap: return AK_2;
                    283:      case k3KeyMap: return AK_3;
                    284:      case k4KeyMap: return AK_4;
                    285:      case k5KeyMap: return AK_5;
                    286:      case k6KeyMap: return AK_6;
                    287:      case k7KeyMap: return AK_7;
                    288:      case k8KeyMap: return AK_8;
                    289:      case k9KeyMap: return AK_9;
                    290:      
                    291:      case kKP0KeyMap: return AK_NP0;
                    292:      case kKP1KeyMap: return AK_NP1;
                    293:      case kKP2KeyMap: return AK_NP2;
                    294:      case kKP3KeyMap: return AK_NP3;
                    295:      case kKP4KeyMap: return AK_NP4;
                    296:      case kKP5KeyMap: return AK_NP5;
                    297:      case kKP6KeyMap: return AK_NP6;
                    298:      case kKP7KeyMap: return AK_NP7;
                    299:      case kKP8KeyMap: return AK_NP8;
                    300:      case kKP9KeyMap: return AK_NP9;
                    301:        
                    302:      case kF1KeyMap: return AK_F1;
                    303:      case kF2KeyMap: return AK_F2;
                    304:      case kF3KeyMap: return AK_F3;
                    305:      case kF4KeyMap: return AK_F4;
                    306:      case kF5KeyMap: return AK_F5;
                    307:      case kF6KeyMap: return AK_F6;
                    308:      case kF7KeyMap: return AK_F7;
                    309:      case kF8KeyMap: return AK_F8;
                    310:      case kF9KeyMap: return AK_F9;
                    311:      case kF10KeyMap: return AK_F10;
                    312:        
                    313:      case kBackSpaceKeyMap: return AK_BS;
                    314:      case kTabKeyMap: return AK_TAB;
                    315:      case kReturnKeyMap: return AK_RET;
                    316:      case kEscapeKeyMap: return AK_ESC;
                    317:      
                    318:      case kSpaceBarMap: if (Joy) return -1; else return AK_SPC;
                    319:      
                    320:      case kUpArrowKeyMap: if (Joy) return -1; else return AK_UP;
                    321:      case kDownArrowKeyMap: if (Joy) return -1; else return AK_DN;
                    322:      case kLeftArrowKeyMap: if (Joy) return -1; else return AK_LF;
                    323:      case kRightArrowKeyMap: if (Joy) return -1; else return AK_RT;
                    324:        
                    325:      case kF11KeyMap: graphics_leave();
                    326:      case kF12KeyMap: { Joy=!Joy; SysBeep(0); return -1; }
                    327: 
                    328:      case kPgUpKeyMap: return AK_RAMI;
                    329:      case kPgDnKeyMap: return AK_LAMI;
                    330:      case kBackSlash: return AK_BACKSLASH;
                    331:     }
                    332:     return -1;
                    333: }
                    334: 
                    335: static int decode_us(long ks)
                    336: {
                    337:     switch(ks) {
                    338:        /* US specific */
                    339: 
                    340:      case kYKeyMap: return AK_Y;
                    341:      case kZKeyMap: return AK_Z;
                    342:      case kLBracketKeyMap: return AK_LBRACKET;
                    343:      case kRBracketKeyMap: return AK_RBRACKET;
                    344:      case kCommaKeyMap: return AK_COMMA;
                    345:      case kPeriodKeyMap: return AK_PERIOD;
                    346:      case kSlashKeyMap: return AK_SLASH;
                    347:      case kSemiColonKeyMap: return AK_SEMICOLON;
                    348:      case kMinusKeyMap: return AK_MINUS;
                    349:      case kEqualKeyMap: return AK_EQUAL;
                    350:      case kQuoteKeyMap: return AK_QUOTE;
                    351:     }
                    352: 
                    353:     return -1;
                    354: }
                    355: 
                    356: static int decode_de(long ks)
                    357: {
                    358:     switch(ks) {
                    359: /* DE specific
                    360:      case XK_Y: case XK_y: return AK_Z;
                    361:      case XK_Z: case XK_z: return AK_Y;
                    362:      case XK_Odiaeresis: case XK_odiaeresis: return AK_SEMICOLON;
                    363:      case XK_Adiaeresis: case XK_adiaeresis: return AK_QUOTE;
                    364:      case XK_Udiaeresis: case XK_udiaeresis: return AK_LBRACKET;
                    365:      case XK_plus: case XK_asterisk: return AK_RBRACKET;
                    366:      case XK_comma: return AK_COMMA;
                    367:      case XK_period: return AK_PERIOD;
                    368:      case XK_less: case XK_greater: return AK_LTGT;
                    369:      case XK_numbersign: return AK_NUMBERSIGN;
                    370:      case XK_ssharp: return AK_MINUS;
                    371:      case XK_apostrophe: return AK_EQUAL;
                    372:      case XK_asciicircum: return AK_00;
                    373:      case XK_minus: return AK_SLASH;       
                    374: */
                    375:     }
                    376: 
                    377:     return -1;
                    378: }
                    379: 
                    380: static int keycode2amiga(long code)
                    381: {
                    382:     long ks;
                    383:     int as;
                    384:     
                    385:     ks = (code & keyCodeMask) >> 8;
                    386:     as = kc_decode (ks);
                    387:        
                    388:     if (as == -1) {        
                    389:        switch(keyboard_lang) {
                    390:         case KBD_LANG_US:
                    391:            as = decode_us(ks);
                    392:            break;
                    393:                
                    394:         case KBD_LANG_DE:
                    395:            as = decode_de(ks);
                    396:            break;
                    397:                
                    398:         default:
                    399:            as = -1;
                    400:            break;
                    401:        }
                    402:     }
                    403:     if(-1 != as)
                    404:        return as;
                    405:     return -1;
                    406: }
                    407: 
                    408: void handle_events()
                    409: {
                    410:     Boolean repeat;
                    411:     Boolean itHappened;
                    412:     Point   mpos;
                    413:     EventRecord event;
                    414:     int kc,i,count;
                    415:        
                    416:     SetEventMask(-1);
                    417:     SelectWindow(mywin);
                    418:     HideCursor();
                    419:        
                    420:     GetKeys(keys);
                    421:     if (BitTst(&keys, kCommandRawKey))
                    422:        RM=true;
                    423:     else
                    424:        RM=false;
                    425:     
                    426:     if (BitTst(&keys, kShiftRawKey))
                    427:     {  
                    428:        if (!keystate[AK_LSH]) {
                    429:            keystate[AK_LSH] = true;
                    430:            record_key (AK_LSH << 1);
                    431:            goto label1;
                    432:        }
                    433:     } else {
                    434:        if (keystate[AK_LSH]) {
                    435:            keystate[AK_LSH] = false;
                    436:            record_key ((AK_LSH << 1) | 1);
                    437:            goto label1;
                    438:        }
                    439:     }
                    440:     if (BitTst(&keys, kControlRawKey))
                    441:     {  
                    442:        if (!keystate[AK_CTRL]) {
                    443:            keystate[AK_CTRL] = true;
                    444:            record_key (AK_CTRL << 1);
                    445:            goto label1;
                    446:        }
                    447:     } else {   
                    448:        if (keystate[AK_CTRL]) {
                    449:            keystate[AK_CTRL] = false;
                    450:            record_key ((AK_CTRL << 1) | 1);
                    451:            goto label1;
                    452:        }
                    453:     }
                    454:     if (BitTst(&keys, kOptionRawKey))
                    455:     {  
                    456:        if (!keystate[AK_LALT]) {
                    457:            keystate[AK_LALT] = true;
                    458:            record_key (AK_LALT << 1);
                    459:            goto label1;
                    460:        }
                    461:     } else {
                    462:        if (keystate[AK_LALT]) {
                    463:            keystate[AK_LALT] = false;
                    464:            record_key ((AK_LALT << 1) | 1);
                    465:            goto label1;
                    466:        }
                    467:     }
                    468:     do {
                    469:        repeat = false;
                    470:        newmousecounters = false;
                    471:        itHappened=WaitNextEvent(-1,&event,0L,0L);
                    472: 
                    473:        switch(event.what) {
                    474:         case keyDown:
                    475:         case autoKey: {        
                    476:             int kc = keycode2amiga(event.message);
                    477:             if (kc == -1) break;
                    478:             if (RM == true && kc == AK_Q) graphics_leave();
                    479:             switch (kc) {
                    480:              case AK_mousestuff:
                    481: #if 0
                    482:                 if (keystate[AK_CTRL])
                    483:                     mousesetup();
                    484:                         else 
                    485: #endif
                    486:                     togglemouse();
                    487:                         break;
                    488: 
                    489:              case AK_inhibit:
                    490:                         inhibit_frame ^= 1;
                    491:                         break;
                    492: 
                    493:              default:
                    494:                 if (!keystate[kc]) {
                    495:                     keystate[kc] = true;
                    496:                     record_key (kc << 1);
                    497:                 }
                    498:                 break;
                    499:             }
                    500:             break;
                    501:         }
                    502:         case keyUp: {       
                    503:             if (Joy) break;
                    504:             kc = keycode2amiga(event.message);
                    505:             if (kc == -1) break;
                    506:             keystate[kc] = false;
                    507:             record_key ((kc << 1) | 1);
                    508:             break;
                    509:         }
                    510:         case mouseDown:
                    511:            if (RM == true) buttonstate[2] = true;
                    512:            else buttonstate[0] = true;
                    513:            break;
                    514:         case mouseUp:
                    515:            buttonstate[0] = false;
                    516:            buttonstate[2] = false;
                    517:            break;
                    518:        }
                    519:        GetMouse(&mpos);
                    520:        if (mpos.h != lastmx) { lastmx=mpos.h; repeat = true; }
                    521:        if (mpos.v != lastmy) { lastmy=mpos.v; repeat = true; }
                    522:     } while (repeat);
                    523:     
                    524: label1:
                    525:     /* "Affengriff" */
                    526:     if(keystate[AK_CTRL] && keystate[AK_LAMI] && keystate[AK_RAMI])
                    527:        MC68000_reset();
                    528: }
                    529: 
                    530: bool debuggable()
                    531: {
                    532:     return true;
                    533: }
                    534: 
                    535: bool needmousehack()
                    536: {
                    537:     return true;
                    538: }
                    539: 
                    540: void LED(int on)
                    541: {
                    542: }
                    543: 
                    544: void parse_cmdline ()
                    545: {
                    546:     /* No commandline on the Mac. Implemented on Menus soon!*/
                    547: }
                    548: 
                    549: // Check Minimal System Configuration and Setup
                    550: static Boolean CheckForSetup (void)
                    551: {      Boolean                 retvalue=FALSE;
                    552:        SysEnvRec               env;
                    553:        
                    554:        SysEnvirons( 2, &env );
                    555:        
                    556:        if ( env.systemVersion < 0x0700 )
                    557:        {       ParamAString("\pUAE requires System 7 or later!");
                    558:                DisplayError(kQuitError);
                    559:                retvalue=TRUE;
                    560:        }
                    561:        if ( !env.hasColorQD)
                    562:        {       ParamAString("\pUAE requires Color QuickDraw!");
                    563:                DisplayError(kQuitError);
                    564:                retvalue=TRUE;
                    565:        }
                    566:        if ( env.processor < 3)
                    567:        {       ParamAString("\pUAE requires a 68020 or better processor to run!");
                    568:                DisplayError(kQuitError);
                    569:                retvalue=TRUE;
                    570:        }
                    571:        curDevice = GetMainDevice();
                    572:        if ((*curDevice)->gdPMap == NULL || (*(*curDevice)->gdPMap)->pixelSize != 16)
                    573:        {       if (HasDepth(curDevice,16,0,0) == 0)
                    574:                {       ParamAString("\pUAE requires 16 bit color and your display doesn't support it!");
                    575:                        DisplayError(kQuitError);
                    576:                        retvalue=TRUE;
                    577:                }
                    578:                else
                    579:                {
                    580:                oldDepth=(*(*curDevice)->gdPMap)->pixelSize;
                    581:                SetDepth(curDevice,16,0,0);
                    582:                }
                    583:        }
                    584:        return(retvalue);
                    585: }
                    586: 
                    587: // Shows up the standard error alert;
                    588: int DisplayError(int ID)
                    589: {      int     ret=0;
                    590: 
                    591:        InitCursor();
                    592:        ret=Alert(ID,0);
                    593: 
                    594:        return (ret);
                    595: }
                    596: 
                    597: // Parses a Pascal string for error display
                    598: void ParamAString( ConstStr255Param theStr )
                    599: {
                    600:        ParamText(theStr, "\p", "\p", "\p");
                    601: }

unix.superglobalmegacorp.com

This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.