Annotation of nono/debugger/debugger_memory.cpp, revision 1.1.1.1

1.1       root        1: //
                      2: // nono
                      3: // Copyright (C) 2020 nono project
                      4: // Licensed under nono-license.txt
                      5: //
                      6: 
                      7: // なんだろう。メモリアクセスヘルパー?
                      8: 
                      9: #include "debugger_private.h"
                     10: #include "mystring.h"
                     11: 
                     12: // コンストラクタ
                     13: DebuggerMemoryStream::DebuggerMemoryStream(const DebuggerMD *md_,
                     14:        const saddr_t& laddr_, MemoryMode access_mode, MMULookupMode lookup_mode)
                     15: {
                     16:        md = md_;
                     17:        laddr = laddr_;
                     18:        // lookup はここで enum から bool にしておく
                     19:        lookup = static_cast<bool>(lookup_mode);
                     20:        // 物理アドレスの時はこれだけでいいので最初に代入しておく
                     21:        paddr = (uint32)laddr;
                     22: 
                     23:        if (access_mode == MemoryMode::Logical && md->MMUEnabled()) {
                     24:                translate = true;
                     25:                // FormatAddr() なしで Fetch/Peek を実行した場合でも、初回に
                     26:                // アドレス変換を起こさせるため。SetNBreakpoint() で使う。
                     27:                pageover = true;
                     28:        }
                     29: }
                     30: 
                     31: // 現在のアドレスを表示用に整形して str に代入する。
                     32: // アドレス変換でバスエラーが起きたら false を返す。
                     33: bool
                     34: DebuggerMemoryStream::FormatAddr(std::string& str)
                     35: {
                     36:        // ここは pageover に関係なく必ずアドレス変換を行う。
                     37:        // (その結果必ず pageover = false になる)
                     38: 
                     39:        if (translate) {
                     40:                // laddr は論理アドレスなのでアドレス変換する
                     41:                uint64 tmp = md->TranslateAddr(laddr, lookup);
                     42:                pageover = false;
                     43: 
                     44:                // laddr は常に表示
                     45:                str = string_format("%08x", (uint32)laddr);
                     46: 
                     47:                if ((int64)tmp < 0) {
                     48:                        // アドレス変換の結果バスエラーなら false で帰る
                     49:                        str += ":BusErr";
                     50:                        return false;
                     51:                }
                     52: 
                     53:                paddr = (uint32)tmp;
                     54:                if (paddr == (uint32)laddr) {
                     55:                        // PA==VA
                     56:                        str += "=PA";
                     57:                } else {
                     58:                        // PA!=VA
                     59:                        str += string_format(":%08x:", paddr);
                     60:                }
                     61:        } else {
                     62:                // laddr は物理アドレスなのでそのまま
                     63:                paddr = (uint32)laddr;
                     64: 
                     65:                str = string_format("%08x:", paddr);
                     66:        }
                     67: 
                     68:        return true;
                     69: }
                     70: 
                     71: // アドレスをリセットする。
                     72: // (他のパラメータは維持するので、1ワード戻るとかそういう時用)
                     73: void
                     74: DebuggerMemoryStream::ResetAddr(uint32 newaddr)
                     75: {
                     76:        if (((newaddr ^ (uint32)laddr) & 0xffffff00) != 0) {
                     77:                pageover = true;
                     78:        }
                     79:        laddr = newaddr;
                     80:        paddr = newaddr;
                     81: }
                     82: 
                     83: // 前回のアクセスでページ境界をまたいだかも知れない場合は再変換。
                     84: #define PRECHECK() do {        \
                     85:        if (__predict_false(pageover)) {        \
                     86:                uint64 tmp = md->TranslateAddr(laddr, lookup);  \
                     87:                if ((int64)tmp < 0) {   \
                     88:                        return (uint64)-2;      \
                     89:                }       \
                     90:                paddr = (uint32)tmp;    \
                     91:                pageover = false;       \
                     92:        }       \
                     93: } while (0)
                     94: 
                     95: // 論理アドレスがページ境界をまたいだかどうか。
                     96: // m68k はページサイズが 256バイト..32KB まで可変だが、いつ変わるか
                     97: // 分からないページサイズマスクを取得することを考えたら、多少の無駄
                     98: // を承知で常に 256 バイトおきにチェックするほうがマシかもしれない。
                     99: #define POSTCHECK() do {       \
                    100:        if (__predict_false(translate && (paddr & 0xff) == 0)) {        \
                    101:                pageover = true;        \
                    102:        }       \
                    103: } while (0)
                    104: 
                    105: 
                    106: // laddr から単位命令語を読み込むが、アドレスは進めない。
                    107: uint64
                    108: DebuggerMemoryStream::PeekInst()
                    109: {
                    110:        uint64 data;
                    111: 
                    112:        assert(((uint32)laddr & (md->inst_bytes - 1)) == 0);
                    113: 
                    114:        PRECHECK();
                    115: 
                    116:        data = 0;
                    117:        for (int i = 0; i < md->inst_bytes; i++) {
                    118:                data <<= 8;
                    119:                data |= vm_phys_peek_8(paddr + i);
                    120:        }
                    121: 
                    122:        return data;
                    123: }
                    124: 
                    125: // laddr から単位命令語を読み込んで、アドレスを進める。
                    126: uint64
                    127: DebuggerMemoryStream::FetchInst()
                    128: {
                    129:        uint64 data;
                    130: 
                    131:        data = PeekInst();
                    132:        laddr += md->inst_bytes;
                    133:        paddr += md->inst_bytes;
                    134: 
                    135:        POSTCHECK();
                    136: 
                    137:        return data;
                    138: }
                    139: 
                    140: // laddr から1バイト読み込んで、アドレスを進める。
                    141: uint64
                    142: DebuggerMemoryStream::Fetch8()
                    143: {
                    144:        uint64 data;
                    145: 
                    146:        PRECHECK();
                    147: 
                    148:        data = vm_phys_peek_8(paddr);
                    149:        laddr++;
                    150:        paddr++;
                    151: 
                    152:        POSTCHECK();
                    153: 
                    154:        return data;
                    155: }

unix.superglobalmegacorp.com

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