Signetics 2650 & 2636 编程/2650 处理器
2650 最初由 Signetics 于 1975 年发布。[1] 这些游戏机使用的是 2650A,它是一个经过重新设计的版本,体积更小,制造成本更低,并且具有改进的操作余量。2650A 于 1977 年发布。[2] 后来,2650B 版本进行了一些设计更改并增加了功能,但这里我们不关心这些。2650 是用 NMOS 制成的,与 TTL 兼容,其许多控制信号使其易于连接。Adam Osborne 将其描述为非常类似于小型机的设备,它与 IBM 1130 非常相似。它具有许多独特的功能
- 32k 字节地址范围,组织为四个 8k 字节页面。
- 可变长度指令,长度为 1、2 或 3 字节。
- 单比特 I/O 路径(标志和检测引脚)。
- 包括间接和索引在内的多种寻址模式。
- 矢量中断。
- 八级返回地址栈。
- 七个 8 位寄存器。
- 两个程序状态字节。
- 强大的指令集。
2650 有七个通用 8 位寄存器。R0 始终可用,而 R1、R2 和 R3 有两个组,它们由程序状态字中的 RS 位选择。
程序状态字 (PSW) 是一个特殊用途寄存器,它包含状态和控制位。它分为两个字节,即程序状态上 (PSU) 和程序状态下 (PSL)。可以使用tpsu、tpsl、lpsu、lpsl、spsu、spsl、ppsu、ppsl、cpsu 或 cpsl 指令测试、加载、存储、预置或清除 PSW 位。
|
| ||||||||||||||||||||||||||||||||||
|
当将复位脉冲应用于 2650A 时,程序执行将被迫从内存地址 0 开始。关于复位后处理器状态的唯一确定信息是程序状态字中的中断禁止位已清除。由于我们非常不希望发生自发中断,因此我们的程序应该首先做的第一件事之一就是将其设置为禁用它们,直到我们准备好它们为止。“Signetics 2650 初始化应用备忘录”还建议我们可以将堆栈指针设置为零,并且我们应该将寄存器选择位设置为已知状态。[5]
带进位位和比较位可以设置为在第一次需要它们时的任何状态。在一个简单程序中,它们在整个程序中处于相同状态,这是一个直接的决定。在更复杂的程序中,通常最好先将它们设置为最常用的状态,然后在需要相反状态时来回切换。如果带进位位打开,则应在第一个算术指令之前适当地初始化进位位。否则,无需初始化进位或任何其他位(条件码、位间进位或溢出)。 [5]
在 PVI 中发生某些事件会导致它通过将中断 线置低来向 2650 信号它需要关注。如果程序状态字中的中断禁止位未设置(换句话说,中断已启用),则处理器将完成当前指令,然后设置中断禁止位。然后,PVI 将其中断向量 3 输出到数据总线,处理器执行 ZBSR(分支到页面零子程序)到地址 $0003。
中断服务子程序完成后,应该使用 RETC 或 RETE 指令退出。后者将重新启用中断。
2650A 指令集中的所有助记符都是 3 或 4 个字符。前两个或三个字符指定操作,如果有的话,最后一个字符表示要使用的寻址模式(有关详细信息,请参阅下一节,寻址模式)。2650 的汇编代码通常如下所示
loop: lodi,r0 $20 ; load r0 from the byte immediately following, $20 stra,r0 $1F40 ; store r0 in the absolute address $1F40 eorz r0 ; exclusive-or r0 with itself bctr,un loop ; branch relative, unconditionally, to address specified by 'loop'
有 34 条基本指令
传输 | LOD | Z,I,R,A | 加载寄存器 |
STR | Z,R,A | 存储寄存器 | |
算术 | ADD | Z,I,R,A | 加到寄存器 |
SUB | Z,I,R,A | 从寄存器中减去 | |
DAR | 十进制调整寄存器 | ||
逻辑 | AND | Z,I,R,A | 按位与到寄存器 |
IOR | Z,I,R,A | 按位或到寄存器 | |
EOR | Z,I,R,A | 按位异或到寄存器 | |
测试 | COM | Z,I,R,A | 将值与寄存器比较 |
TM | I | 测试寄存器的掩码位 | |
旋转 | RRR | 将寄存器向右旋转一位 | |
RRL | 将寄存器向左旋转一位 | ||
分支 | BCT | R,A | 如果条件为真,则分支 |
BCF | R,A | 如果条件为假,则分支 | |
BRN | R,A | 如果寄存器不为零,则分支 | |
BIR | R,A | 递增寄存器,如果它不为零,则分支 | |
BDR | R,A | 递减寄存器,如果它不为零,则分支 | |
ZBR | R | 分支,相对于地址 $0000 | |
BX | A | 分支,索引 | |
调用/返回 | BST | R,A | 如果条件为真,则分支到子程序 |
BSF | R,A | 如果条件为假,则分支到子程序 | |
BSN | R,A | 如果寄存器不为零,则分支到子程序 | |
ZBS | R | 分支到子程序,相对于地址 $0000 | |
BSX | A | 分支到子程序,索引 | |
RET | C,E | 有条件地从子程序返回。 RETE 还启用中断 | |
输入/输出 | WRT | C,D,E | 这些游戏机上没有实现输入/输出硬件 |
RED | C,D,E | ||
其他 | HALT | 进入等待状态,直到处理器复位或中断 | |
NOP | 除了获取和执行此指令之外什么也不做 | ||
程序状态字 | LPS | U,L | 加载 PSW |
SPS | U,L | 存储 PSW | |
CPS | U,L | 清除 PSW 中的指定位 | |
PPS | U,L | 预置 PSW 中的指定位 | |
TPS | U,L | 测试 PSW 中的指定位 |
Signetics 2650 有四种主要的寻址方式:寄存器、立即、相对和绝对。此外,间接和索引寻址可以与其中一些方式组合使用。
所有寄存器到寄存器的指令都是 1 字节长,并使用 R0 作为第一个操作数,而另一个操作数可以是 R0、R1、R2、R3 中的任何一个。
lodz r3 ; load r0 from r3 addz r2 ; r0 = r0 + r2 lodz r0 ; not very useful! eorz r0 ; exclusive-or r0 with itself ; very useful! A one byte instruction for r0 = 0
在立即寻址中,第一个操作数(可以是任何寄存器)在指令旁边指定;后面跟着另一个操作数的值,该操作数隐式地必须是一个常量。所有立即寻址指令都是 2 字节长。
lodi,r2 $20 ; r2 = 32 subi,r0 8 ; r0 = r0 - 8 iori,r1 %00100000 ; set bit5 of r1 comi,r3 15 ; compare r0 to 15
在绝对寻址中,第一个操作数(可以是任何寄存器(但请参阅下面的索引寻址中的异常))在指令旁边指定。第二个参数指定另一个操作数所在的内存位置的绝对地址。
在相对寻址中,第一个操作数(可以是任何寄存器)在指令旁边指定。第二个参数指定另一个操作数所在的内存位置。这个第二个参数是相对于当前地址的相对位移,可以是 -64 到 +63 之间的任何值。在实践中,我们不将此值指定为数字。它通常采用标签的形式,汇编器会为我们进行计算。如果标签距离太远,汇编器将生成错误消息。相对寻址也用于分支指令,以跳转到附近的内存位置。
lodr,r2 number ; r2 = 42 bctr,un next ; branch to next number: db 42 ; define a data byte = 42 next: addi,r2 53
当使用索引寻址时,有效地址通过将指定索引寄存器的内容添加到地址字段来计算。加法使用索引寄存器中的值作为 8 位正数。
lodi,r2 5 loda,r0 $1F00,r2 ; r0 = contents of address $1F05
请注意,第一个参数始终是 r0。一些汇编器可能允许从代码中省略它,但为了可读性,应尽可能包含它。
另外两个选项允许在索引寄存器添加到基地址之前自动递减或自动递增。
lodi,r2 5 loda,r0 $1F00,r2+ ; r0 = contents of address $1F06 lodi,r3 $A6 loda,r0 $1000,r3- ; r0 = contents of address $10A5
索引只能与绝对寻址一起使用。它不能与分支指令一起使用,但有两个特殊指令用于此目的。它们是 BXA(分支索引,绝对)和 BSXA(分支到子程序索引,绝对)。自动递增和自动递减不能与它们一起使用,并且必须指定寄存器 R3 作为索引寄存器。
间接寻址意味着指令的参数地址不是由指令本身指定的,而是参数地址将在指令指向的两个字节中找到。间接寻址模式由星号 (*) 表示。
pointer dw $0F00 ; in most cases this would be an address in RAM, i.e. a variable ..... loda,r1 *pointer ; r1 = contents of $0F00
间接寻址也可以与相对寻址一起使用,但由于这些控制台中代码是从 ROM 中运行的,并且 RAM 地址通常距离太远而无法进行相对寻址,因此没有明显的用途。当代码空间非常宝贵时,会出现一个例外。
:bar equ $1F0E 0000 066A : lodi,r2 $6A 0002 CE1F0E : stra,r2 bar 0005 0D1F0E :foo loda,r1 bar 0008 0BFC : lodr,r3 *foo+1 ; load r3 indirectly from $0006, i.e. $1F0E
最后两个指令都从bar加载一个寄存器,但最后一个指令只使用了两个字节而不是三个字节。
当索引和间接寻址一起使用时,索引寄存器的值将添加到间接地址,而不是添加到指令的地址字段中的值。
有关更多详细信息,请查阅Signetics 2650 用户手册,该手册以完整 pdf 格式或针对程序员的 html 缩写版提供。
- ↑ 微型计算机文摘 (PDF). 库比蒂诺,加利福尼亚州:微型计算机协会。2 (1): 1–3. 1975 年 7 月 http://bitsavers.trailing-edge.com/magazines/Microcomputer_Digest/Microcomputer_Digest_v02n01_Jul75.pdf. 存档 (PDF) 于 2014 年 2 月 1 日从原文中. 检索于 2021 年 12 月 4 日.
{{cite journal}}
: Cite has empty unknown parameter:|1=
(help); Invalid|url-access=2021 年 12 月 4 日
(help); Missing or empty|title=
(help) - ↑ "Signetics 2650: An IBM on a Chip". CPUshack 博物馆. 2016 年 10 月 16 日. 检索于 2021 年 12 月 5 日.
{{cite web}}
: Check date values in:|date=
(help) - ↑ 奥斯本,亚当 (1978). 微型计算机导论 (PDF). 伯克利,加利福尼亚州:奥斯本与合伙人。p. 736. ISBN 0-931988-15-2. 检索于 2021 年 11 月 4 日.
- ↑ 2650 系列微处理器数据手册 (PDF). 飞利浦. 检索于 2021 年 11 月 4 日.
- ↑ a b Signetics 应用备忘录 MP51 - 2650 初始化 (PDF). 飞利浦. 检索于 2021 年 11 月 4 日.