Windows Subsystem for Linux 概述

Windows Subsystem for Linux 概述

之前的一篇文章,我曾经写过【Bash On Windows】在 Windows Subsystem for Linux(WSL) 上运行任何桌面环境(已达可用阶段),有很多人对这方面的内容比较感兴趣。因此,在微软官方的网站上找到了一些关于 Windows Subsystem for Linux 的介绍文档。

本文主要对 WSL(Windows Subsystem for Linux )进行概述。

内容由微软实习生@戴秉璋 翻译,出自微软官方:原文链接

在设计之初,微软就允许类似于Win32这种子系统运行于windows NT内核之上,它可以为上层应用提供编程接口,同时避免应用去实现内核里的一些调用细节。NT内核的设计在最开始就可以支持POSIX,OS/2和win32子系统。

早先的子系统是用户态模块的实现,它封装了NT系统的系统调用为应用程序提供编程接口。所有的应用程序都是PE/COFF(一些为子系统封装NT系统调用的库和服务)可执行的。当一个用户态的程序启动的时候,启动器就会基于可执行的头部去引用适当的子系统来满足应用程序的依赖。

后来版本的子系统替换掉了POSIX层,由用户态组件提供了Subsystem for Unix-based Applications (SUA),满足:

1. 进程和信号管理

2. 终端管理

3. 系统服务请求和进程间通信

SUA的主要目的是为了鼓励应用程序移植到Windows上能尽量少的重写。这已经通过实现POSIX用户态API达到了。考虑到这些组件是用户态实现,很难跟内核态的系统调用(比如fork())在语义上和效率上完全相对应。因为这种模式需要程序重新编译,它需要持续的功能移植,维护也是负担。

随着时间的演变,这些早先的子系统都退出历史舞台了。但是因为WIndows NT内核的架构允许新的子系统环境,我们就基于这领域的原始积累进行扩展,发展Windows Subsystem for Linux。

Windows Subsystem for Linux

WSL是一些组件的集合,允许原生的Linux ELF64二进制文件跑在Windows上。它同时包括了用户态和内核态组件,主要包含以下部分:

1. 用户态会话管理服务处理Linux实例的生命周期

2. Pico provider drivers (lxss.sys, lxcore.sys)“翻译”系统调用,以模拟Linux内核

3. Pico 进程管理原生的用户态Linux(比如/bin/bash)

奇迹就发生于用户态的Linux二进制文件和Windows内核组件之间。通过将未经修改的Linux二进制文件放置于Pico进程中,我们把Linux系统调用直接导入Windows内核中。lxss.sys, lxcore.sys驱动将Linux系统调用翻译为NT APIs,来模拟Linux内核。

Pico进程

作为Project Drawbridgemicrosoft.com/en-us/res的一部分,Windows内核引入了Pico进程和Pico驱动的概念。Pico进程和驱动提供了Windows Subsystem for Linux的基础。可执行的ELF二进制文件被加载到Pico进程的地址空间,并在系统调用的Linux兼容层上执行。

系统调用

WSL基于Windows NT内核虚拟了Linux内核接口,这允许它执行未经修改的Linux ELF64二进制文件。一类内核接口是系统调用。系统调用是内核为用户态程序提供的一种服务。Linux内核和Windows NT内核都为用户态程序提供了几百个系统调用,但是他们有不同的语义,并且一般来说并不直接兼容。比如Linux提供fork, open和kill,Windows NT提供相兼容NtCreateProcess, NtOpenFile和 NtTerminateProcess。

Windows Subsystem for Linux 包含内核态驱动(lxss.sys和 lxcore.sys),以协调Linux系统调用的请求与Windows NT内核。驱动不包含Linux内核代码,但是是一个全新实现的Linux兼容的内核接口。在原生的Linux上,用户态程序请求一个系统调用,系统调用请求由Linux内核处理。在WSL,当一个系统调用由同一个可执行文件请求时,Windows NT内核把请求发送给lxcore.sys。 当可能时,lxcore.sys将Linux系统调用翻译成等价的Windows NT的调用,由它来完成繁重的工作。当没有可能的等价转换时,Windows内核态驱动需要直接处理请求。

比如说,Linux中的fork()系统调用没有直接的等价的windows版本。当一个fork系统调用由Windows Subsystem for Linux产生时,lxcore.sys需要做一些复制进程的准备工作,然后调用Windows NT内核APIs来产生一个进程来正确实现fork操作,完成为新进程复制额外的数据。

文件系统

WSL支持的文件系统需要满足两个目标。

1. 提供一个完全支持Linux文件系统的环境

2. 能够与Windows上的设备和文件互通

Windows Subsystem for Linuxt提供与真实Linux内核类似的虚拟文件系统。在用户的系统上,我们提供了两个文件系统:VolFs 和 DriveFs。

VolFs

VolFs提供了完整的Linux文件系统特性的支持,包括:

1. Linux权限管理,访问权限可以通过如chmod和chroot来改变

2. 文件的符号链接

3. 文件名可以包含一些Windows上不合法的符号

4. 大小写敏感

包含Linux系统的目录,应用程序文件(/etc, /bin, /usr等)和用户Linux家目录都使用的是VolFs。

与Windows应用和文件的互用在VolFs里并不支持。

DriveFs

DriveFs是为了和windows互用的文件系统。它需要所有的文件名是合法的windows文件名,使用Windows安全策略,并不完整地支持所有的Linux文件系统特性。文件名是大小写敏感的,用户不允许创建仅仅是大小写不同的两个文件。

所有的Windows磁盘使用DriveFs被挂在到/mnt/c,/mnt/d等等下面。用户从这里可以访问所有Window下的文件。这允许用户用他们喜欢的Windows编辑器比如Visual Studio Code来编辑文件的同时,通过Bash里的一些开源工具来修改文件。


文章如有错误,请各位专家评论“指点”,必将第一时间更正。

编辑于 2016-08-04

文章被以下专栏收录

    微软信仰中心,帮你充值微软信仰! 欢迎加入微软信仰中心 Skype 群?:http://t.cn/RtoniBj 和我一起聊微软! 偶尔会发布一些微软官方商城的优惠活动信息!