LogicalSpaceMonitor.java
     1: //========================================================================================
     2: //  LogicalSpaceMonitor.java
     3: //    en:Logical space monitor
     4: //    ja:論理空間モニタ
     5: //  Copyright (C) 2003-2024 Makoto Kamada
     6: //
     7: //  This file is part of the XEiJ (X68000 Emulator in Java).
     8: //  You can use, modify and redistribute the XEiJ if the conditions are met.
     9: //  Read the XEiJ License for more details.
    10: //  https://stdkmd.net/xeij/
    11: //========================================================================================
    12: 
    13: package xeij;
    14: 
    15: import java.awt.*;  //BasicStroke,BorderLayout,BoxLayout,Color,Component,Container,Cursor,Desktop,Dimension,Font,FlowLayout,Frame,Graphics,Graphics2D,GraphicsDevice,GraphicsEnvironment,GridLayout,Image,Insets,Paint,Point,Rectangle,RenderingHints,Robot,Shape,Stroke,TexturePaint,Toolkit
    16: import java.awt.event.*;  //ActionEvent,ActionListener,ComponentAdapter,ComponentEvent,ComponentListener,FocusAdapter,FocusEvent,FocusListener,InputEvent,KeyAdapter,KeyEvent,KeyListener,MouseAdapter,MouseEvent,MouseListener,MouseMotionAdapter,MouseWheelEvent,WindowAdapter,WindowEvent,WindowListener,WindowStateListener
    17: import java.lang.*;  //Boolean,Character,Class,Comparable,Double,Exception,Float,IllegalArgumentException,Integer,Long,Math,Number,Object,Runnable,SecurityException,String,StringBuilder,System
    18: import javax.swing.*;  //AbstractButton,AbstractSpinnerModel,Box,ButtonGroup,DefaultListModel,ImageIcon,JApplet,JButton,JCheckBox,JCheckBoxMenuItem,JComponent,JDialog,JFileChooser,JFrame,JLabel,JList,JMenu,JMenuBar,JMenuItem,JPanel,JRadioButton,JScrollPane,JSpinner,JTextArea,JTextField,JTextPane,JViewport,ScrollPaneConstants,SpinnerListModel,SpinnerNumberModel,SwingConstants,SwingUtilities,UIManager,UIDefaults,UnsupportedLookAndFeelException
    19: 
    20: public class LogicalSpaceMonitor {
    21: 
    22:   public static JFrame atwFrame;  //ウインドウ
    23:   public static final ScrollTextArea[] atwBoard = new ScrollTextArea[2];  //スクロールテキストエリア
    24:   public static final JTextArea[] atwTextArea = new JTextArea[2];  //テキストエリア
    25: 
    26:   //atwInit ()
    27:   //  初期化
    28:   public static void atwInit () {
    29:     atwFrame = null;
    30:   }  //atwInit()
    31: 
    32:   //atwStart ()
    33:   public static void atwStart () {
    34:     if (RestorableFrame.rfmGetOpened (Settings.SGS_ATW_FRAME_KEY)) {
    35:       atwOpen ();
    36:     }
    37:   }  //atwStart()
    38: 
    39:   //atwOpen ()
    40:   //  アドレス変換ウインドウを開く
    41:   //  既に開いているときは手前に持ってくる
    42:   public static void atwOpen () {
    43:     if (atwFrame == null) {
    44:       atwMake ();
    45:     }
    46:     atwUpdate ();
    47:     atwFrame.setVisible (true);
    48:     XEiJ.dbgVisibleMask |= XEiJ.DBG_ATW_VISIBLE_MASK;
    49:   }  //atwOpen()
    50: 
    51:   //atwMake ()
    52:   //  アドレス変換ウインドウを作る
    53:   public static void atwMake () {
    54: 
    55:     for (int m = 0; m < 2; m++) {
    56:       //スクロールテキストエリア
    57:       atwBoard[m] = ComponentFactory.setPreferredSize (
    58:         ComponentFactory.setFont (new ScrollTextArea (), LnF.lnfMonospacedFont),
    59:         550, 250);
    60:       atwBoard[m].setMargin (new Insets (2, 4, 2, 4));
    61:       atwBoard[m].setHighlightCursorOn (true);
    62:       atwTextArea[m] = atwBoard[m].getTextArea ();
    63:       atwTextArea[m].setEditable (false);
    64:     }
    65: 
    66:     //テキストエリアのマウスリスナー
    67:     ComponentFactory.addListener (
    68:       atwTextArea[0],
    69:       new MouseAdapter () {
    70:         @Override public void mousePressed (MouseEvent me) {
    71:           if (XEiJ.mpuTask == null && me.isPopupTrigger ()) {
    72:             XEiJ.dbgShowPopup (me, atwTextArea[0], false);
    73:           }
    74:         }
    75:         @Override public void mouseReleased (MouseEvent me) {
    76:           if (XEiJ.mpuTask == null && me.isPopupTrigger ()) {
    77:             XEiJ.dbgShowPopup (me, atwTextArea[0], false);
    78:           }
    79:         }
    80:       });
    81:     ComponentFactory.addListener (
    82:       atwTextArea[1],
    83:       new MouseAdapter () {
    84:         @Override public void mousePressed (MouseEvent me) {
    85:           if (XEiJ.mpuTask == null && me.isPopupTrigger ()) {
    86:             XEiJ.dbgShowPopup (me, atwTextArea[1], false);
    87:           }
    88:         }
    89:         @Override public void mouseReleased (MouseEvent me) {
    90:           if (XEiJ.mpuTask == null && me.isPopupTrigger ()) {
    91:             XEiJ.dbgShowPopup (me, atwTextArea[1], false);
    92:           }
    93:         }
    94:       });
    95: 
    96:     //ボタンのアクションリスナー
    97:     ActionListener listener = new ActionListener () {
    98:       @Override public void actionPerformed (ActionEvent ae) {
    99:         Object source = ae.getSource ();
   100:         switch (ae.getActionCommand ()) {
   101:         case "Update":
   102:           atwUpdate ();
   103:           break;
   104:         }
   105:       }
   106:     };
   107: 
   108:     //ウインドウ
   109:     atwFrame = Multilingual.mlnTitle (
   110:       ComponentFactory.createRestorableSubFrame (
   111:         Settings.SGS_ATW_FRAME_KEY,
   112:         "Logical space monitor",
   113:         null,
   114:         ComponentFactory.createBorderPanel (
   115:           ComponentFactory.createVerticalSplitPane (
   116:             ComponentFactory.createVerticalBox (
   117:               ComponentFactory.createHorizontalBox (
   118:                 Multilingual.mlnText (ComponentFactory.createLabel ("User mode"), "ja", "ユーザモード"),
   119:                 Box.createHorizontalGlue ()
   120:                 ),
   121:               atwBoard[0]
   122:               ),
   123:             ComponentFactory.createVerticalBox (
   124:               ComponentFactory.createHorizontalBox (
   125:                 Multilingual.mlnText (ComponentFactory.createLabel ("Supervisor mode"), "ja", "スーパーバイザモード"),
   126:                 Box.createHorizontalGlue ()
   127:                 ),
   128:               atwBoard[1]
   129:               )
   130:             ),
   131:           ComponentFactory.createHorizontalBox (
   132:             Multilingual.mlnToolTipText (
   133:               ComponentFactory.createImageButton (
   134:                 XEiJ.createImage (
   135:                   20, 14,
   136:                   "11111111111111111111" +
   137:                   "1..................1" +
   138:                   "1.......1111.......1" +
   139:                   "1......111111.1....1" +
   140:                   "1.....11....111....1" +
   141:                   "1....11.....111....1" +
   142:                   "1....11....1111....1" +
   143:                   "1....11............1" +
   144:                   "1....11............1" +
   145:                   "1.....11....11.....1" +
   146:                   "1......111111......1" +
   147:                   "1.......1111.......1" +
   148:                   "1..................1" +
   149:                   "11111111111111111111",
   150:                   LnF.lnfRGB[0],
   151:                   LnF.lnfRGB[12]),
   152:                 "Update", listener),
   153:               "ja", "更新"),
   154:             Box.createHorizontalGlue ()
   155:             )
   156:           )
   157:         ),
   158:       "ja", "論理空間モニタ");
   159:     ComponentFactory.addListener (
   160:       atwFrame,
   161:       new WindowAdapter () {
   162:         @Override public void windowClosing (WindowEvent we) {
   163:           XEiJ.dbgVisibleMask &= ~XEiJ.DBG_ATW_VISIBLE_MASK;
   164:         }
   165:       });
   166: 
   167:   }  //atwMake()
   168: 
   169:   //atwUpdate ()
   170:   //  アドレス変換ウインドウを更新する
   171:   public static void atwUpdate () {
   172:     for (int m = 0; m < 2; m++) {
   173:       StringBuilder sb = new StringBuilder ();
   174:       sb.append (Multilingual.mlnJapanese ?
   175:                  //xxxxxxx-xxxxxxxx  xxxxxxxx-xxxxxxxx
   176:                  "  論理アドレス       物理アドレス\n" :
   177:                  " Logical address   Physical address\n");
   178:       int l0 = 0x00000000;
   179:       int p0 = MC68060.mmuTranslatePeek (l0, m, 0);
   180:       int f0 = MC68060.mmuPeekFlags;
   181:       if ((p0 ^ l0) == 1) {
   182:         p0 = 1;
   183:       }
   184:       int l1 = MC68060.mmuPageSize;
   185:       while (l1 != 0x00000000) {
   186:         int p1 = MC68060.mmuTranslatePeek (l1, m, 0);
   187:         int f1 = MC68060.mmuPeekFlags;
   188:         if ((p1 ^ l1) == 1) {
   189:           p1 = 1;
   190:         }
   191:         if (!(p0 == 1 && p1 == 1 ||
   192:               p0 != 1 && p1 != 1 && p1 - p0 == l1 - l0 && f0 == f1)) {
   193:           if (p0 != 1) {
   194:             XEiJ.fmtHex8 (XEiJ.fmtHex8 (XEiJ.fmtHex8 (XEiJ.fmtHex8 (sb, l0).append ('-'), l1 - 1).append ("  "), p0).append ('-'), p0 + (l1 - l0) - 1).append (' ');
   195:             if ((f0 & MC68060.MMU_DESCRIPTOR_SUPERVISOR_PROTECTED) != 0) {
   196:               sb.append (Multilingual.mlnJapanese ? " [スーパーバイザ]" : " [Supervisor]");
   197:             }
   198:             if ((f0 & MC68060.MMU_DESCRIPTOR_MODIFIED) != 0) {
   199:               sb.append (Multilingual.mlnJapanese ? " [修正済み]" : " [Modified]");
   200:             }
   201:             if ((f0 & MC68060.MMU_DESCRIPTOR_USED) != 0) {
   202:               sb.append (Multilingual.mlnJapanese ? " [使用済み]" : " [Used]");
   203:             }
   204:             if ((f0 & MC68060.MMU_DESCRIPTOR_WRITE_PROTECTED) != 0) {
   205:               sb.append (Multilingual.mlnJapanese ? " [書き込み禁止]" : " [Write-protected]");
   206:             }
   207:             sb.append ('\n');
   208:           }
   209:           l0 = l1;
   210:           p0 = p1;
   211:           f0 = f1;
   212:         }
   213:         l1 += MC68060.mmuPageSize;
   214:       }
   215:       if (p0 != 1) {
   216:         XEiJ.fmtHex8 (XEiJ.fmtHex8 (XEiJ.fmtHex8 (XEiJ.fmtHex8 (sb, l0).append ('-'), l1 - 1).append ("  "), p0).append ('-'), p0 + (l1 - l0) - 1).append (' ');
   217:         if ((f0 & MC68060.MMU_DESCRIPTOR_SUPERVISOR_PROTECTED) != 0) {
   218:           sb.append (Multilingual.mlnJapanese ? " [スーパーバイザ]" : " [Supervisor]");
   219:         }
   220:         if ((f0 & MC68060.MMU_DESCRIPTOR_MODIFIED) != 0) {
   221:           sb.append (Multilingual.mlnJapanese ? " [修正済み]" : " [Modified]");
   222:         }
   223:         if ((f0 & MC68060.MMU_DESCRIPTOR_USED) != 0) {
   224:           sb.append (Multilingual.mlnJapanese ? " [使用済み]" : " [Used]");
   225:         }
   226:         if ((f0 & MC68060.MMU_DESCRIPTOR_WRITE_PROTECTED) != 0) {
   227:           sb.append (Multilingual.mlnJapanese ? " [書き込み禁止]" : " [Write-protected]");
   228:         }
   229:         sb.append ('\n');
   230:       }
   231:       atwTextArea[m].setText (sb.toString ());
   232:       atwTextArea[m].setCaretPosition (0);
   233:     }
   234:   }  //atwUpdate()
   235: 
   236: }  //class LogicalSpaceMonitor
   237: 
   238: 
   239: