**Netwide Assembler** （简称 **NASM**）是一款基于英特尔 x86 架构的汇编与反汇编工具。它可以用来编写 16位、32位（IA-32）和 64位（x86-64）的程序。 NASM 被认为是 Linux 平台上最受欢迎的汇编工具之一。

NASM 最初是在朱利安·霍尔的协助下由西蒙·泰瑟姆开发的。 截至2016年 (2016-Missing required parameter 1=*month*!)[update]，它被一个由 H.Peter Anvin 领导的小团队所维护。 它是一款基于简化版（二句版）BSD许可证的开放源代码软件。

功能
--

NASM 可以输出包括 COFF、OMF、a.out、可执行与可链接格式（ELF）、Mach-O 和二进制文件（.bin，二进制磁盘映像，用于编译操作系统）等多种二进制格式，而地址无关代码仅支持 ELF 对象文件。 NASM 也有自己的二進位格式，稱為 RDOFF。

输出格式的广泛性允许将程序重定向到任何 x86 操作系统（OS）。 此外，NASM 可以创建浮动二进制文件，它可用于写入引导加载程序、只读存储器（ROM）映像以及操作系统开发的各个方面。 NASM 可以作为交叉汇编程序（如 PowerPC 和 SPARC）在非 x86 平台上运行，尽管它不能生成这些机器可用的程序。

NASM 使用英特尔语法的变体而不是 AT&T 语法（GNU 汇编器采用的语法）。 它还避免了 MASM 和兼容汇编器使用的自动生成區段覆盖（以及相关的 ASSUME 指令）等功能。

用于各种操作系统的示例程序
-------------

这是一个 DOS 操作系统下的 "Hello world!" 程序：

```
section .text
org 0x100
 mov ah, 0x9
 mov dx, hello
 int 0x21

 mov ax, 0x4c00
 int 0x21

section .data
hello: db 'Hello, world!', 13, 10, '$'

```
一个类似程序在 Microsoft Windows 下的示例：

```
global \_main
extern \_MessageBoxA@16
extern \_ExitProcess@4

section code use32 class=code
\_main:
 push dword 0 ; UINT uType = MB\_OK
 push dword title ; LPCSTR lpCaption
 push dword banner ; LPCSTR lpText
 push dword 0 ; HWND hWnd = NULL
 call \_MessageBoxA@16

 push dword 0 ; UINT uExitCode
 call \_ExitProcess@4

section data use32 class=data
 banner: db 'Hello, world!', 0
 title: db 'Hello', 0

```
一段 Linux 下的等价程序：

```
global \_start

section .text
\_start:
 mov eax, 4 ; write
 mov ebx, 1 ; stdout
 mov ecx, msg
 mov edx, msg.len
 int 0x80 ; write(stdout, msg, strlen(msg));

 mov eax, 1 ; exit
 mov ebx, 0
 int 0x80 ; exit(0)

section .data
msg: db "Hello, world!", 10
.len: equ $ - msg

```
下面是一个用于苹果 macOS（原為 OS X）的 64 位元程序，用于输入按键并将其显示在屏幕上：

```
global \_start

section .data

 query\_string: db "Enter a character: "
 query\_string\_len: equ $ - query\_string
 out\_string: db "You have input: "
 out\_string\_len: equ $ - out\_string

section .bss

 in\_char: resw 4

section .text

\_start:

 mov rax, 0x2000004 ; put the write-system-call-code into register rax
 mov rdi, 1 ; tell kernel to use stdout
 mov rsi, query\_string ; rsi is where the kernel expects to find the address of the message
 mov rdx, query\_string\_len ; and rdx is where the kernel expects to find the length of the message 
 syscall

 ; read in the character
 mov rax, 0x2000003 ; read system call
 mov rdi, 0 ; stdin
 mov rsi, in\_char ; address for storage, declared in section .bss
 mov rdx, 2 ; get 2 bytes from the kernel's buffer (one for the carriage return)
 syscall

 ; show user the output
 mov rax, 0x2000004 ; write system call
 mov rdi, 1 ; stdout
 mov rsi, out\_string
 mov rdx, out\_string\_len
 syscall

 mov rax, 0x2000004 ; write system call
 mov rdi, 1 ; stdout
 mov rsi, in\_char
 mov rdx, 2 ; the second byte is to apply the carriage return expected in the string
 syscall

 ; exit system call
 mov rax, 0x2000001 ; exit system call
 xor rdi, rdi
 syscall

```

链接
--

NASM 主要输出目标文件（扩展名一般为 .obj），这些目标文件通常不能自行执行。唯一的例外是浮动二进制文件（例如 .COM） ，它们在现代使用中固有地受到限制。 要将目标文件转换为可执行程序，必须使用适当的链接程序，例如用于 Windows 的 Visual Studio"LINK"实用程序或用于类 Unix 系统的 ld。

发展
--

第一版（版本号0.90）发布于1996年10月。

2007年11月28日，2.00版本发布，增加对 x86-64 扩展的支持。 开发版本不再上传到 SourceForge.net；相反，它们会被检入到项目自己的 Git 存储库中，而其二进制程序的快照可在项目官网上找到。

一个用于 NASM 文档的搜索引擎也已可用。

截至 2.07 版本，NASM 在简化 BSD 许可证（二句版）下发布。

RDOFF
-----

开发人员使用可重定位的动态对象文件格式（RDOFF）来测试 NASM 的目标文件输出能力的完整性。它很大程度上基于 NASM 的内部结构，主要由一个头部组成，头部包含输出驱动程序函数调用的序列化，后跟包含可执行代码或数据的部分数组。 NASM 发行版中包含了使用该格式的工具，包括链接程序 (linker) 和加载程序 (loader)。

直到1996年10月发布 0.90 版，NASM 才支持只输出浮动格式的可执行文件（例如 DOS 的 COM 文件）。在版本 0.90 中，Simon Tatham 增加了对一个目标文件输出接口的支持，并且只支持用于 16 位元代码的 DOS 的 .OBJ 文件。

NASM 因此缺少一个 32 位元的格式。 为了解决这个问题，作为学习对象文件接口的练习，开发人员朱利安·霍尔将第一版 RDOFF 发布于 NASM 0.91 版本。

自从这个初始版本以来，对 RDOFF 格式进行了一次重大更新，它在每个标题记录上增加了一个记录长度指示器， 允许程序跳过它们无法识别格式的记录，并支持多个區段；RDOFF1 仅支持三個區段：，和 bss（包含未初始化的数据）。

另请参见
----

* 汇编语言
* 汇编器列表
* Yasm

参考文献
----

1. ↑  .
2. ↑  Ram Narayan..  [2018-03-29]. （原始内容存档于2013-10-03）. two of the most popular assemblers for Linux, GNU Assembler (GAS) and Netwide Assembler (NASM)
3. ↑ .  [2008-06-27]. （原始内容存档于2008-07-24）.
4. ↑ .  [2009-07-19]. （原始内容存档于2009-07-04）.
5. ↑ .  [2009-08-15]. （原始内容存档于2009-02-23）.
6. ↑  Randall Hyde..  [2008-06-27]. （原始内容存档于2010-09-12）.
7. ↑ .  [2017-04-23]. （原始内容存档于2017-05-01）.
8. ↑ .  [2009-09-14]. （原始内容存档于2010-01-23）.
9. ↑ .  [2008-06-27]. （原始内容存档于2008-07-24）.
10. ↑ . 2008-06-08  [2008-06-27]. （原始内容存档于2022-04-07）.
11. ↑ . 2002-12-04  [2008-06-27]. （原始内容存档于2022-04-07）.

进一步阅读
-----

* Jeff Duntemann.. J Wiley and Sons. 2000. ISBN 0-471-37523-3.

外部链接
----

* 官方网站
* SourceForge.net上的Netwide Assembler

* Special edition for Win32 and BeOS.
* A comparison of GAS and NASM（页面存档备份，存于） at IBM
* Freecode（英语：）上的Netwide Assembler: a converter between the source format of the assemblers NASM and GAS

Freshmeat1intel2gas

|  |  |  |  |  |  |  |  |  |  |  |
| --- | --- | --- | --- | --- | --- | --- | --- | --- | --- | --- |
| 

| * 
* 论
* 编
x86 汇编器与汇编语言 |
| --- |
|  |
| 相关话题 | 
* 汇编语言
* 汇编语言与汇编器列表
* 反汇编器
* 指令集架構
* 低级语言
* 机器语言
* 微汇编程序（英语：）
* x86汇编语言（英语：）

 |
|  |
| 汇编器 | 
* A86（英语：）
* FASM（英语：）
* GNU 汇编器（GAS）
* 高階組合語言（HLA）
* 微软宏汇编器（MASM）
* NASM
* TASM（英语：）
* WASM（英语：）
* Yasm

 |
|  |
| 使用汇编语言编程 | 
* 调用栈
* 标志寄存器（英语：）
	+ 进位标志（英语：） （CF）
	+ 方向标志（英语：）（DF）
	+ 中断标志（英语：）（IF）
	+ 溢出标志（英语：）（OF）
	+ 零标志（英语：）（ZF）
* 操作码（英语：）
* 程式計數器
* 寄存器与x86寄存器
* 调用约定
* 指令列表（英语：）

 |

 |