Windows NT 3.1 1991 年 4 月版本
| Windows NT 3.1 的版本 | |
翻转棋在 x86 模拟下运行 | |
| 操作系统系列 | Windows NT 系列 |
|---|---|
| 内核版本 | 4.0[1] |
| 体系结构 | MIPS R3000 |
| 编译日期 | 1991 年 4 月 4 日 |
Windows NT 3.1 1991 年 4 月版本是 Windows NT 3.1 的早期版本,它是目前最早的 Windows NT 版本。2023 年 11 月 4 日,PCjs 网站的开发人员兼前 Microsoft 员工 Jeff Parsons 将标有“WOW Reversi MIPS Demo”的磁盘映像添加到 PCjs 其他软盘存储库中,其中包含带有版本文件的 ZIP 压缩文件。[2]
此版本是针对 Microsoft Jazz 体系结构的早期版本编译的,此体系结构早于 MIPS R4000 处理器的发布。因此,它实际上针对的是早期的 R3000 处理器,它与 R4000 并不完全兼容。
在每周一次的“Thursday Beers”活动中,此版本用于在 Windows 上运行的翻转棋和 MIPS 机器上的 x86 仿真的内部演示。[3]这个演示对于翻转棋来说令人难忘,因为 GDI 还不能画圆形或曲线。[3][4]此版本的 GDI 实现的基元仅包括线条、矩形和文本。此外,仅支持纯色画笔。根据内部谈话,GDI 直到 1991 年 6 月才计划完成代码。[5]
通过模拟器模拟

可以使用 modified version of MAME 的修改版本来模拟此版本,该版本添加了基于 R3000 的自定义 Jazz 机器。为了启动版本,还必须通过串行端口将运行 OS/2 上 MIPSKD.EXE 的另一个虚拟机(位于磁盘 #1 上的 NT.ZIP)连接到 MAME 实例。
构建模拟器
假设事先准备好了开发环境,请在 MAME 源码目录下执行以下命令:
$ make -j8 SUBTARGET=r3000jazz SOURCES=src/mame/microsoft/r3kjazz.cpp
编译成功后,将在克隆的存储库中生成一个 r3000jazz 可执行文件。
设置 OS/2 以进行调试
此版本需要附加内核调试器,并且会在启动早期中断。建议设置一个 OS/2 2.0 虚拟机,此虚拟机具有可连接到 MAME 以运行随附 MIPSKD.EXE 的串行端口。请确保在 OS/2 设置期间启用串行端口,否则将无法访问它。
串行端口可以在 VirtualBox 中配置为与 MAME 和 NTSerialPort 一起使用,如下所示:
- 打开设置(Settings)
- 转到“Serial Ports(串行端口)”选项卡
- 选中“Enable Serial Port checkbox(启用串行端口复选框)”
- 将端口号设置为 COM1
- 将端口模式设置为 TCP
- 取消选中“Connect to existing pipe/socket(连接到现有管道/socket)”复选框
- 将路径/地址设置为 31337
通过将整个 NT 安装复制到 C:\NTOLD 中,然后使用磁盘 #1 中的 DEBUG.CMD 启动调试器,而不是直接运行 MIPSKD.EXE,可以(尽管不是必需的)设置调试符号。
运行 NT
- 启动内核调试器(kernel debugger)。
- 如果在 VirtualBox 中运行调试器,请启动 NTSerialTool。
- 使用
$ ./r3000jazz r3000jazz -serial0 null_modem -bitb socket.127.0.0.1:31338 -hard1 <path to disk image> -window运行 MAME,其中<path-to-disk-image>是使用 NT 的磁盘映像的路径。 - 通过在 ARC 固件中运行
\ntoskrnl来启动 NT。
此时,日志消息应开始出现在调试器中,最终到达 NT SM> 提示符。此版本通常会中断调试器;如果发生这种情况,请在调试器中键入 g,然后按 Enter。
如果 ARC 固件在启动时显示 NVRAM 警告或找不到内核文件,请转到“运行安装程序(Run setup)”>“初始化系统(Initialize system)”>“设置默认配置(Set default configuration)”,在所有提示符下按 Enter,然后退出设置。
模拟器问题
串口波特率
模拟期望串行端口以 9600 bps 的速度运行。某些虚拟器(如 VirtualBox)发送数据的速度可能会超过预期的波特率,从而导致调试器无法正常工作。
NTSerialTool 可用于限制波特率。首先需要设置调试器虚拟机的串行端口,以便它侦听 TCP 端口 31337。尝试运行版本时,请先启动 VM,然后运行 NTSerialTool,然后使用连接到 TCP 端口 31338 的串行端口启动 MAME。如果配置正确,该工具将显示它已连接到 MAME。
光标
硬件光标当前没有模拟,因此光标不可见。鼠标单击仍然可以工作,但是无法看到光标会使与操作系统交互变得困难。使用键盘快捷键进行导航可能更容易。
SCSI 错误
可能会发生随机 SCSI 错误,很可能是由于模拟器中的错误。目前没有解决此问题的解决方法,如果弹出 SCSI 错误,则必须重置模拟计算机。
品牌
由于其原始性质,该版本包含不一致的品牌:
- 内部版本号(由
BASESRV.DLL中的BaseGetConnectInformation函数设置,用于更新BASE.DLL中的GetVersion函数返回的全局变量)设置为 4.0;命令行 shell(CMD.EXE)同样将自身标识为 Windows Version 4.0 Command Interpreter; - 配置文件和内核通过其原始项目名称 NT OS/2 来标识操作系统;
- 图形 shell 中的桌面将操作系统称为 NT 32 位 Windows(性质类似于 Build 175 和 196),而系统的其他方面只是将其称为 NT;
- 许多文件描述利用 Windows 32 命名。
目录布局
| 路径 | 存档 | 包含 | |||
|---|---|---|---|---|---|
\
|
NT.ZIP(磁盘 #1)
|
内核、配置文件和会话管理器 | |||
Nt
|
— | — | |||
Bin
|
NTBIN.ZIP(磁盘 #2)
|
大多数可执行文件 | |||
Bin86
|
NTBIN86.ZIP(磁盘 #2)
|
x86 模拟器使用的磁盘映像和保存状态 | |||
Dll
|
NTDLL.ZIP(磁盘 #3)
|
库 | |||
SubSys
|
NTSUBSYS.ZIP(磁盘 #2)
|
子系统可执行文件 | |||
Windows
|
NTWIN.ZIP(磁盘 #2)
|
WIN.INI
| |||
Fonts
|
— | 字体文件 | |||
Windows-on-Windows
这是已知最早包含 Windows-on-Windows(WoW)的版本,这是一个允许 32 位 Windows 运行 16 位 DOS 和 Windows 应用程序的兼容层。此版本中的环境基于 MS-DOS 5.00 Build 336 和 Windows 3.1 的早期版本,它们由 x86 仿真器(X86.EXE))从两个磁盘映像(DOS500.DSK 和 WOW.DSK)加载。这与后来的版本有显著区别,后者直接从磁盘加载系统文件文件,因为主机文件系统通过 NTVDM 传递到 DOS 环境。此外,x86 模拟器是一个内部项目,而不是零售版附带的 SoftPC 定制版本。Jeff Parsons 于 2023 年 11 月 14 日发布了此模拟器更高版本的源代码,即原始版本上传后 10 天。[6]
包括 Windows 3.0 中的日历、翻转棋和记事本,而系统的其余部分则可以追溯到 1991 年 1 月 25 日至 1991 年 3 月 20 日,早于 Windows 3.1 最早的可用版本 Build 026。还包括 HELLO.EXE 和 GENERIC.EXE 示例应用程序。日期为 1991 年 3 月 18 日的 USER.DLL 在某个时候从磁盘中删除。由于此版本中的 SHELL.DLL(包含显示版本和内部版本信息的“关于”对话框)不包括在内,因此无法确定确切的内部版本号。
REVERSI.HOT
REVERSI.HOT(位于 C:\Nt\Bin86;NTBIN86.ZIP 位于磁盘 #2 上)是在 x86 仿真下此版本运行翻转棋的状态保存。前 640 KiB 存储 x86 虚拟机的内存内容。接下来的 88 个字节描述了寄存器和其他数据的状态。最后 2000 个字节包含 Windows 进入图形模式之前控制台上的每个字符(80×25 个字符)。准备此文件可能是为了节省初始化 MS-DOS、16 位 Windows 和在模拟下加载翻转棋所需的时间,这可能会占用大量时间。
在 16 位 Windows 进入图形模式之前,屏幕上的文本(注:之所以显示 dte 而不是 date(日期),这是由于 x86 模拟器在打印小写字符 a 时存在问题):
Current dte is Sun 01-06-1980
Enter new dte (mm-dd-yy):
Current time is 5:59:56.58
Enter new time:
Microsoft(R) MS-DOS(R) Version 5.00.336ß
(C)Copyright Microsoft Corp 1981-1990.
A>b:
B>kernel reversi.exe
B:\SYSTEM.INI
状态的保存可以通过输入 l <path-to-save-file> 来加载,并通过在 x86 仿真器提示符下输入 s <path-to-save-file> 来创建。
-
状态保存
REVERSI.HOT已恢复。 -
从
REVERSI.HOT恢复后运行的翻转棋。
控制台模式

此版本包括控制台子系统的早期实现,此子系统与 GDI(默认启用)不兼容。为了启动控制台应用程序(如 CMD.EXE),需要首先通过将 NTOS2.CFG 中的子系统行设置为以下值来启用控制台子系统:
SubSystem = \SystemDisk\Nt\SubSys\csrss.exe ObjectDirectory=\Windows SubSystemType=Windows ServerDll=basesrv,1 ServerDll=consrv,2
控制台模式不能与SM提示符同时运行,因为提示符会阻止所有代码执行。通过在提示符中输入 DELAY -1 命令或将其设置为 NTOS2.CFG 中的 InitialCommand 来运行此命令将有效地禁用 SM 提示符,并允许控制台模式任务管理器将自身绘制到屏幕上并接受输入。然后,可以通过选择“启动程序”选项并按 Enter 键来启动默认 shell。但是,这样做会导致断言失败,这是控制台句柄取消引用失败的结果。
API 差异
此版本拥有 Win32 API 的原始版本。缺少许多常用函数,仅支持 ANSI 字符集,使其成为唯一可用的 NT 版本,每个涉及字符串的函数都没有双变体(ANSI 和 Wide)。此外,GRE 和 USER 必须分别通过调用 Initialize 和 InitWindows 来手动初始化。还值得注意的是,不支持W WinMain,所有程序(原生、控制台和 GUI)只能使用 C 样式的 main 函数作为入口点。因此,当前实例的句柄通常是通过线程环境块中的进程环境块获取的。
与 Build 196 相比,图形呈现引擎在单独的 DLL(GRE.DLL)中实现,而不是 GDI 服务器 DLL(GDISRV.DLL)的一部分。这类似于 OS/2 中 GPI 和图形引擎的分离。
Bug
- 可见分辨率限制为 1024×1024,即使实际显示分辨率为 1280×1024。屏幕最右边的部分被黑条覆盖,但如果拖动到此区域,窗口轮廓仍会呈现。这是由于硬编码 1024x1024 作为窗口站桌面窗口的尺寸(
xxxCreateWindowEx(0, 0x8001, NULL, WS_POPUP | WS_CLIPCHILDREN, 0, 0, 1024, 1024, NULL, NULL, hModuleWin, NULL))。可以通过将USERSRV.DLL偏移量 0x47D05 处的字节从04更改为05来修复此错误。 - 字母“a”在 x86 模拟器窗口中未正确显示,也无法将其输入到任何 WOW 进程中。
图库
-
图形驱动程序显示的调色板
-
x86 模拟器
-
x86 模拟器运行 MS-DOS
-
Win32 测试应用程序
-
PlgBlt 调色板
-
WOW 下的翻转棋
-
WOW 下的 Hello
-
WOW 下的通用示例应用程序
-
WOW 关于对话框
引用资料
- ↑ 仅为 Windows Command Interpreter 的版本,非 Windows NT 内核版本
- ↑ https://github.com/jeffpar/pcjs-miscdisks/commit/745b046f85939929f6b87baa8e573d2517adc657
- ↑ 3.0 3.1 John Lam(2022 年 6 月 6 日). "Ep.9 Larry Osterman:在 Microsoft 工作了 37 年,从 MS-DOS 到 Azure,并就如何在公司拥有长期而富有成效的职业生涯提供建议". Pivotal Moments with John Lam(Podcast). 事件发生在 28:04。检索于 2023 年 11 月 21 日.
- ↑ Raymond Chen. 随机内部 Windows 术语:IDW、Razzle 及其被遗忘的合作伙伴 IDS 和 Dazzle, Old New Thing. 2018 年 12 月 24 日.
- ↑ Comes v. Microsoft. 原告的证物 427. Microsoft Confidential.
- ↑ https://github.com/jeffpar/pcjs-miscdisks/commit/08a7f5475a0816b9abf9aaa49645681451f92052