資料集
ここはhideyosiの学習帳です。いろいろな資料を集めたり整理したりしています。オイラ用のノートなので間違っていたり未完成だったりしますので信用度は相当低いことをあらかじめご了承くださいませ。

くっそ!アカン!どうも理解が甘い!以下は間違ってます!(お勉強&再整理開始・・・)


  • 桁指定の考え方は、基本は全て指定しよ!ってことでいいのかな・・・
  • たとえばレジスタ相手。これだって、「指定して間違い」ってわけじゃないはず。ええと・・・
MOV    AX,0x11        ←まあ問題ないよね?相手がAXなんだからイヤでも16ビット

MOV    AX, WORD 0x11  ←無駄ではあるが、これは「間違い」だろうか??

・・・ふむ・・・実験の結果、少なくとも「間違いではない」ようだ・・・

こういうのはおかしくなるかな???

MOV    WORD AX,WORD 0x11

あれれれ?? これも正常にコンパイルできたなぁ。これも、「別に間違いではない」って理解でいいのかな??

たとえばこうしたとするよね?

MOV    [0x00ff],0x11

これが間違いなのは分る。正解は

MOV    [0x00ff],WORD 0x11

これでコンパイルが通る。・・・しかし疑問だ。

  • 最初の、アドレスを指定している部分。ここ、0x00ffって言うけど、これが0xffなのか、0x00ffなのか、0x000000ffなのか・・・って、おい!!!

あ〜! そっか!なるほどなるほど!。そうだよ!アドレス指定の場合は、[0xff]も[0x00ff]も[0x000000ff]も同じことじゃないか!!!

ん?じゃあもしかして・・・・

MOV   WORD [0x00ff],WORD 0x11

これもいいの???

あっちゃぁ〜。いいんじゃん!(エラーないし、同じバイナリが出てくる)

うーん。しかしそうなると分らん。P37の、 MOV BYTE [678],123 。これはどう理解すれば・・・

あーーー!! まってまって??。勘違いしてたかも!?

値の桁数はわからないってのがおかしいのか。だって、0x11も0x0011も0x00000011も値としてはまったく同じことなんだよね???

メモリのほうに桁指定を入れるってのはようするに、「メモリ素子何個使う?」っていう理解でいいのかな????

・・・そうすると、たとえば

MOV BYTE [678],0x11223344

こんなことしたらどうなるの????

あー・・・エラーになる。じゃ、これは?

MOV BYTE [678],0x00000044

おーーーー!! エラー出ない!!!!!!

こんな実験もしてみた。

MOV AX,0x00000044    ←エラーなし

MOV AX,0x11223344    ←エラー!!

おぉ!予測どおり!しかも、 MOV AX,0x11223344 と MOV BYTE [678],0x11223344 は、同じエラー(data range error.)が出る!! 分ってきたぞ!!!

じゃあこれはどうなる?

たとえば0x10番地に0x11、0x11番地に0x22を入れておいたとして・・・
MOV AX, [0x10]       ← これは分る。AXには、0x2211が代入されるはず。
MOV AX, BYTE [0x10] ← こうやればAXには0x0011が入るのか?
                        おーー! エラー!

さらにこんなの・・・

MOV AL,BYTE 0x11223344

うほ!エラーだよ!!!。しかもデータレンジのエラー!

・・・わかってきたぞ・・・。NASK(あるいはアセンブラ?)では、とにもかくにも、「切捨ては決してしない」ってことなんじゃないのか???

こういう法則かなぁ・・・ anchor.png Edit

  • アセンブラでは、全ての代入に桁指定をする
  • 補完はするが、決して切り捨てをしない

相手がレジスタだろうがなんだろうが、とにかく全て桁を指定する!

当たり前だが、桁指定と指定された物が矛盾してはいけない。

MOV    WORD AX,WORD 0x1122

MOV    BYTE [0x0043],BYTE 0x11

MOV    WORD [0x0044],WORD DX

※どれも問題ない。とにかく全て桁を指定する。

問題がある指定

指定と矛盾する
MOV    BYTE AX,BYTE 0x13     ← AXは16bitのレジスタ。BYTE指定はおかしい
切捨ては決してしてくれない
MOV    BYTE AL,BYTE 0x11223344 ←たとえBYTE指定しても、0x11223344は8bitデータじゃない。
                                  (自動で0x11223344を0x44に切り捨てしたりしてくれない)
以下は問題がない(補完)
MOV    WORD AX, WORD 0x11   ←0x11と0x0011は同じこと。WORD指定で頭00を補完してくれる

MOV    WORD AX,WORD 0x00000011  ←一見切り捨てに見えるが、0x00000011と0x11はまったく同じこと。
                                  なので、「元々0x11だった」と理解すれば、補完になる

以上の単純な法則で全てOK。これで少なくとも「間違いである!」ということは起きなくなる

Page Top

実際の書き方(省略) anchor.png Edit

上記の簡単な法則が全て。後は、「省略しても特定できるかどうか」だけとなる。

省略しても特定できるのでエラーにならない例

MOV    WORD AX,WORD 0x1122    ←本来の書き方
MOV    AX,WORD 0x1122         ←AXは16bitレジスタと解りきっているので省略可
MOV    AX,0x1122              ←但し注意。これは0x1122が16bitと特定できるのではない。
                                ・AXが16bitなんだから、当然値も16bitだろう
                                ・うん、4桁だし、問題もないよね?
                                と、こう理解しているに過ぎない。

MOV    WORD DX,WORD 0x11      ←本来の書き方
MOV    DX,WORD 0x11           ←DXは16bitに特定できる。0x11も0x0011と同じ
                                なのでWORD指定しても矛盾しない(補完)
MOV    DX,0x11                ←上の例と同じで、0x11を見て判断しているのではない。
                                あくまでもDX(本来ならWORD DX)によって16bitに
                                特定され、0x11は16bit化しても矛盾しないので
                                エラーにならないに過ぎない。

MOV BYTE [0x0041],BYTE 0x22    ←本来の書き方(エラーにならない)
MOV BYTE [0x0041],0x22         ←・メモリに対しBYTE指定。当然値もBYTEだろう。
                                 ・0x22はBYTE指定と矛盾しないな。OK!
                                 ・エラーにならない。
MOV [0x0041],BYTE 0x22         ←・メモリにバイト指定がないなぁ。何バイトだ?
                                 ・うん、値にはBYTE指定か。じゃあメモリをBYTEと
                  決め付けても問題ないだろう。
                                 ・エラーにならない
  • 下2例のメモリへのMOV。メモリ側と値側。とにかくどちらか一方でも指定があれば他方は特定できる。・・・じゃ、どっちを省略するのが正しい??
  • 少なくともどちらを省略してもエラーにはならない。それどころかどちらを省略しても、また省略しなくても、出てくるバイナリはまったく同一である。
    MOV BYTE [0x0041],BYTE 0x22   ←┐
    MOV BYTE [0x0041], 0x22       ←┼── 全て同じこと。バイナリも同一
    MOV [0x0041],BYTE 0x22        ←┘

特定ができない例:(エラーになる)

MOV [0x0041],0x11              ←・ん?何バイト?メモリにも値にも指定がないぞ?
                                 ・え?値が0x11だからBYTE指定だろうって?
                                 ・それは解らんぞ?もし0x0011なら0x0041番地と0x0042番地
                                   にも書かなくちゃいけない。どっちだ?
                                 ・エラーになる(特定しきれない)

MOV [0x0041],0x1122            ←・これならいいだろう?値は16bit。WORD指定だ!
                                 ・値が0x001122っていう可能性はないの?それ次第
                                   では0x0043にも書かなくちゃいけない。どっち?
                                 ・エラーになる(特定しきれない)

MOV [0x0041],0x11223344        ←・これならどうだ!お前DWORDまでだろう?
                                   値が32bitなんだから、値から32bit(DWORD指定)と
                                   特定できるはずだ!
                                 ・この値がさ、0x000000000011223344じゃないって
                                   保障ある?。ないよね?。やっぱり特定できない。
                                 ・エラーになる(特定しきれない)
  • 省略していいのか悪いのか、ごっちゃになってわからなくなっちゃった!
    • そういう場合はなまじっか考えず、全部指定しちゃうのがいい。そうすれば少なくともエラーにはならないし、正解の省略と出てくるバイナリは変わらない。それでもエラーになるっていうなら、矛盾・切捨て違反のどちらかだと、間違いの特定もできるし。
Page Top

実際の挙動(メモリへの代入) anchor.png Edit

  • 8ビット指定
MOV BYTE [0x0042],0x11      

   :    ├────┤         :    ├────┤
0x40番地 │ 0x32   │      0x40番地 │ 0x32   │
         ├────┤               ├────┤
0x41番地 │ 0xA1   │      0x41番地 │ 0xA1   │
         ├────┤               ├────┤
0x42番地 │ 0x4F   │  ⇒  0x42番地 │ 0x11   │ ←ここだけ変化
         ├────┤               ├────┤
0x43番地 │ 0x96   │      0x43番地 │ 0x96   │
         ├────┤               ├────┤
0x44番地 │ 0xEF   │      0x44番地 │ 0xEF   │
         ├────┤               ├────┤
0x45番地 │ 0x89   │      0x45番地 │ 0x89   │
         ├────┤               ├────┤
0x46番地 │ 0xFF   │      0x46番地 │ 0xFF   │
   :    ├────┤         :    ├────┤
  • 16ビット指定
MOV WORD [0x0042],0x11      

   :    ├────┤         :    ├────┤
0x40番地 │ 0x32   │      0x40番地 │ 0x32   │
         ├────┤               ├────┤
0x41番地 │ 0xA1   │      0x41番地 │ 0xA1   │
         ├────┤               ├────┤
0x42番地 │ 0x4F   │  ⇒  0x42番地 │ 0x11   │ ←値は16ビットの0x0011と
         ├────┤               ├────┤    解釈される。値が16ビット
0x43番地 │ 0x96   │  ⇒  0x43番地 │ 0x00   │  ←なのだから0x43も変化する
         ├────┤               ├────┤    (リトルエンディアンで値が
0x44番地 │ 0xEF   │      0x44番地 │ 0xEF   │     逆さまになるのに注意)
         ├────┤               ├────┤
0x45番地 │ 0x89   │      0x45番地 │ 0x89   │
         ├────┤               ├────┤
0x46番地 │ 0xFF   │      0x46番地 │ 0xFF   │
   :    ├────┤         :    ├────┤
  • 32ビット指定
MOV DWORD [0x0042],0x11      

   :    ├────┤         :    ├────┤
0x40番地 │ 0x32   │      0x40番地 │ 0x32   │
         ├────┤               ├────┤
0x41番地 │ 0xA1   │      0x41番地 │ 0xA1   │
         ├────┤               ├────┤
0x42番地 │ 0x4F   │  ⇒  0x42番地 │ 0x11   │ ←値は32ビットの0x00000011と
         ├────┤               ├────┤    解釈される。値が32ビット
0x43番地 │ 0x96   │  ⇒  0x43番地 │ 0x00   │  ←なのだから0x43、0x44、0x45
         ├────┤               ├────┤    まで変化する
0x44番地 │ 0xEF   │  ⇒  0x44番地 │ 0x00   │  ←(リトルエンディアンで値が
         ├────┤               ├────┤     逆さまになるのに注意)
0x45番地 │ 0x89   │  ⇒  0x45番地 │ 0x00   │  ←
         ├────┤               ├────┤
0x46番地 │ 0xFF   │      0x46番地 │ 0xFF   │
   :    ├────┤         :    ├────┤

Front page   Edit Freeze Diff Backup Upload Copy Rename Reload   New Page Page list Search Recent changes   Help   RSS of recent changes (RSS 1.0) RSS of recent changes (RSS 2.0) RSS of recent changes (RSS Atom)
Counter: 3052, today: 1, yesterday: 0
Last-modified: 2022-06-14 (Tue) 05:52:26 (GMT) (468d) by