Game Boy:什么构成了“半进位”?

40

Game Boy的Z80 CPU有一个半进位标志位,但我似乎找不到关于何时设置/清除它的信息。

目前我的理解是,任何8位加法、减法、移位或旋转操作(可能还有其他操作)都会将其设置为结果的第4位(?),而DAA指令以某种方式设置/使用它。 我不确定的是16位指令如何影响它以及是否受某些寄存器的影响。


嗯,这不是电子问题吗? - Vinayak Garg
19
我正在编写模拟器,所以我不这么认为… - Rena
我强烈建议任何遇到半进位标志问题的人阅读帖子以获取更多详细信息。 - 0x4d45
阅读Z80参考手册。每个指令对所有标志位的影响都有记录。 - TomServo
3个回答

33

这是从第3位到第4位的进位,就像正常进位标志记录了从第7位的进位一样。因此,例如在加法中获取半进位:

((a&0xf) + (value&0xf))&0x10

若需要设置半进位则返回0x10,否则返回0。从其他相关操作中获得半进位自然而然地遵循 - 问题是低四位是否向高四位进位。

为了更好地理解,z80具有4位ALU,并通过执行两个4位操作来执行8位操作。因此,它会很自然地获得半进位作为中间结果。

DAA对此标志感兴趣,因为如果设置了半进位,则在低四位中相加超过16的两个数字将正确地产生进位到高四位,但由于介于10和16之间时应该生成进位,所以低四位将比应有的值少6。


2
好的,但是16位操作呢?半进位是从高字节还是低字节设置的? - Rena
3
高位字节指的是最近半个进位。你可能已经找到了,但我认为http://datasheets.chipdb.org/Zilog/Z80/z80-documented-0.90.pdf对DAA有很好的描述,并解释了像CCF这样的边缘情况下半个进位来自哪里(如果我没记错的话,它被设置为旧的进位)。 - Tommy
2
有一件事需要补充,这让我很清楚:例如添加0x37和0x44不会导致半进位,因为您只查看每个字节的低4位,将它们相加,并查看是否溢出。 0x0F + 0x01会产生半进位,而0x37 + 0x44则不会。 - Michael Stum
GBZ80(又名SM83)具有8位ALU。 - S.S. Anne

11

对于16位操作,寄存器高字节从第3位到第4位的进位将设置标志。换句话说,是第11位到第12位。

(请注意,上面的位从最低有效位标记为0到最高有效位标记为15)

参见这里:http://www.z80.info/z80code.htm

16 bit arithmetic

If  you want to add numbers that are more than the 0-255 that can
be stored in the A register,  then the HL, IX or IY registers can
be used. Thus LD HL,1000H:LD BC,2000H:ADD HL,BC will give

A  CZPSNH  BC   DE   HL   IX   IY  A' CZPSNH' BC'  DE'  HL'  SP
00 000000 2000 0000 3000 0000 0000 00 000000 0000 0000 0000 0000

The flags are set as follows.

C or carry flag          1 if answer >65535 else 0
Z or zero flag           not changed
P flag                   not changed
S or sign flag           not changed
N flag                   0
H or half carry flag     1 if carry from bit 11 to bit 12 else 0

这个问题涉及Game Boy。Sharp SM83的操作方式完全相同,只是它没有预设寄存器集、IX或IY寄存器,也没有P或S标志。 - NoLongerBreathedIn

0

由于半进位标志是Game Boy模拟器制作者最常遇到的障碍之一,我想发表一个关于这个主题的最近问题链接作为答案:

Game Boy:半进位标志和16位指令(特别是操作码0xE8)


以上线程的摘要(由@gekkio回答):

这取决于指令,但如果您从8位值的角度考虑,标志始终基于相同的位位置更新...只是我们谈论16位值的高字节还是低字节有所不同。第11位只是高字节的第3位。

  • ADD SP,e:H来自位3,C来自位7(来自低字节操作的标志)
  • LD HL,SP + e:H来自位3,C来自位7(来自低字节操作的标志)
  • ADD HL,rr:H来自位11,C来自位15(来自高字节操作的标志)
  • INC rr:没有标志更新(由16位inc / dec单元执行)
  • DEC rr:没有标志更新(由16位inc / dec单元执行)

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接