【问题标题】:Why do values are shown/stored in an unsymmetrical way?为什么值以不对称的方式显示/存储?
【发布时间】:2014-06-10 15:25:33
【问题描述】:

我为大学作业编写了一个小程序,它是关于用 3x7 Matrix第二列 减去 1x3 Vector 并将结果存储在 1x3 VectorR .

我已经完成它得到正确的答案,但有件事真的引起了我的注意:

使用 Turbo Debugger 我注意到 Data Segment 中的结果(十六进制值)的存储(或可能只是显示)与我的示例结果不同老师给了:

老师的成绩:

我的结果:

我知道这些结果不同,但它们是正确的。我希望这些值以以下方式存储(例如):

0103
04FD
0606
0A0A
0B0B

但它的存储方式类似于(例如)

0103
04FD06
06
0A0A
0B
0B

据我所知,ds: 和这些值之间的值是内存方向,但我猜它们的长度相同(32 位架构为 32 位),但似乎有些有更多/长度更短。当然这只是我的猜测。所以,我的问题是:

为什么这些值以这种方式存储?在某些方向上拥有像 050908 这样的值,而在其他方向上只有 05 是什么意思?或者...它是否依赖于调试器?

编辑:这是ds 查看程序开头的方式:

  • 红色:一些变量
  • 黄色: Vector
  • 黑色: VectorR

【问题讨论】:

  • 内存中只有字节,没有结构。根据调试信息,不同的打印输出可能只是来自调试器的友好服务。
  • 您只是看到不同的最终结果(为什么?Turbo 调试器专家...去吧)。内容是相同的 - 您可以通过查看实际数据左侧的偏移量来验证。
  • @MichaelFoukarakis 这是有道理的。那么,左边ds:xxxx 中的值是内存地址对吗?
  • @Christian:看起来确实是这样,我猜是这样。

标签: debugging assembly masm tasm


【解决方案1】:

但是十六进制数的顺序是一样的。一个按列格式化,另一个根据说明,可以更长或更短。具有隐式寻址或无寻址的指令比具有后续存储器地址的指令需要更少的空间。在格式化指令列表的第二种情况下,会显示指令长度,而在第一种情况下则不会。当加载到 RAM 中时,这并不重要 - 重要的是序列仍然正确。考虑到呈现给您的布局不同 - 但内存是一维的,好像所有指令都写在一行上 - 这对您来说更难阅读。

(注意:我在上面谈论“说明”,因为所提供的证据只是转储的一小部分,采用子缩略图格式。当时并不清楚显示的数据可能不是说明。)

尽管调试器会尝试从数据中获取意义,但对其进行格式化,使其可以以属于同一行的数据打印在同一行上的方式呈现。调试器不知道,并在它看到的数据中寻找它从数据中得出的线索。因此,不保证数据布局正确。当然,不尝试将含义读入数据的调试器不会在那里失败。调试器可以寻找的一个线索是“这是一个已知指令的操作码,因此我对其进行布局,以便该指令具有的字节数显示在一行上”。所以是的,特定于调试器。

【讨论】:

  • 那么这些值是指令吗?它们不是我所做的操作的值结果吗?由于它们在数据段ds 中,我希望它们“表示”只是数据,而不是指令。
  • 这是将程序的源代码组装或编译成机器可执行表示的结果,由指令和数据组成。指令是一个操作码,后面可能有一些数据。并非所有指令都需要数据,因为只有 opcde。一个示例是 NOP,即“无操作”。另一方面,将固定值加载到注册器中的指令由该指令的操作码和要加载的值组成。很明显,寄存器越宽,数据就必须越长。
  • 数据段中的数据可以通过多种方式到达那里:作为程序的一部分,程序加载器将它们放置在那里,或者作为程序操作的结果,将数据存储在那里。为了更准确地分辨出有什么,需要看到的不仅仅是你放在那里的几行。
  • 我已经编辑了帖子,其中包含一些关于值来自何处的信息。我的问题是:为什么有时连续有 3 个字节或 2 个或 1 个字节?它是否像 MichaelFoukarakis 评论的那样依赖于调试器?
  • 在这种情况下,尝试调试器从数据中获取意义,对其进行格式化,以便可以呈现它,以便将属于一起的数据打印在同一行上。调试器不知道,并在它看到的数据中寻找它从数据中得出的线索。因此,不保证数据布局正确。当然,不尝试将含义读入数据的调试器不会在那里失败。调试器可以寻找的一个线索是“这是一个已知指令的操作码,因此我对其进行布局,以便该指令具有的字节数显示在一行上”。所以是的,调试器特定的。
【解决方案2】:

您正在查看 Turbo Debugger 代码部分中的数据。所以字节将被安排为机器指令。看看你的整个 TD:

您在左上角的部分工作,但数据部分在左下角,在那里您看到“ds:0000...”。执行前两条指令后,它将更改为“es:0000...”,因为DS 的值已更改。现在单击该部分中的任意位置或使用TAB 直到光标在那里闪烁,然后按CTRL-G。输入“DS:0”,该部分将再次显示 DS 段的值。

【讨论】:

  • 我通过File > Table reallocate... > ds访问了ds。你的方式和我的方式都显示完全相同的数据。但在我访问ds 的方式中,调试器似乎以指令可读的方式重新排列它(基于@Bushmills 所说的)。
猜你喜欢
  • 2021-12-04
  • 2016-05-08
  • 2013-09-15
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2013-07-25
  • 1970-01-01
相关资源
最近更新 更多