文档章节

虚拟硬盘VHD的程式化挂载方式

Chen-Zhiqiang
 Chen-Zhiqiang
发布于 2014/02/21 19:15
字数 1589
阅读 4.1K
收藏 32
VHD

行业解决方案、产品招募中!想赚钱就来传!>>>

微软推出的虚拟硬盘vhd同vmdk,qcow2等一样,是一种磁盘镜像格式。磁盘镜像一般多用于虚拟化计算,但微软支持将Win7/Win8/Win2012等直接安装进vhd文件中,并且不通过任何虚拟机,让bootmgr直接引导vhd文件启动系统,就好像这个vhd是真的硬盘一样。

除了方便封装操作系统之外,也有不少工具和方法可以在不同的操作系统下挂载vhd,就好像vhd文件就是移动硬盘一样。因此,vhd也可以是一个不错的数据载体。我将我的程序、数据等归类放到不同的vhd虚拟磁盘中,需要用时可以像移动硬盘那样挂载,需要带走时,复制vhd文件就可以了。

### 使用场景1: Linux

在 Linux下,可以通过QEMU来创建和管理vhd文件。我可以使用 qemu-img 来创建和维护 vhd 文件,通过 qemu-nbd 来挂载 vhd 文件。当然,对 vhdx 格式的管理也不在话下。通过 qemu 可以很方便地管理和维护许多格式的磁盘镜像,而且这些操作都可以通过脚本来完成。事实上,在 Linux 下,对虚拟磁盘的管理要比在 Windows 下强大得多,vhd格式在这里就不起眼了,比如,QEMU 推荐使用的格式是 qcow2。

在 Linux 下,可以编写 shell 脚本来完成虚拟磁盘的挂载等管理工作,并且可以控制这些脚本的执行时机。

另外,如果一个vhd文件是固定大小的,不使用其它工具,仅使用 Linux 的 mount 命令也可以挂载 vhd:

mount [-t <fstype>] -o loop,offset=... <vhd file> <mount point>

offset是第一个分区的偏移量,我的vhd文件都是1M对齐分区的,因此offset是1M。

### 使用场景2: Win7/Win8/Win2012...

在 Win8 下,在资源管理器中点击vhd文件就可以挂载,但在 Win7 上,就要自己写脚本或注册表或是借助第三方工具才能实现这样的操作了。不过,他们都可以在 计算机管理/存储/磁盘管理 这个管理界面上,完成 vhd 的创建、挂载等操作。

但是,虽然 Win7/Win8等可以直接从 vhd 中原生启动,但是他们可不会自动加载我们后来所管理的那些 vhd。而且,问题的重点是,我们需要一种可编程的方式来对 vhd 文件进行管理,而不只是通过图形界面来操作。

Windows所带的 diskpart 似乎可以完成这个工作,比如:

C:\>diskpart
create vdisk file="D:\test.vhd" maximum=2048 type=fixed  ::创建一个固定大小为2G的vhd
select vdisk file="D:\test.vhd"
attach vdisk  ::加载
create partition primary offset=2048 align=4  ::创建分区
active
assign letter=T
format quick fs=ntfs label="TEST"
exit

然而,上面是通过命令行进行交互的,如果是程式化的方式呢?比如,我们需要在开机的时候自动加载几个 vhd 文件,就要以写脚本的方式来做了。

我们可以将一些 diskpart 的指令先写到一个文本文件中,然后调用 diskpart /s <指令文件>,这样,diskpart 就会读取所输入的文件并逐行执行。比如,我们需要在开机时加载若干个vhd文件并指定挂载路径,可以先将相应的diskpart输入指令写到一个文本文件中,假设是C:\diskpart.input.txt,然后,写一个批处理:

@echo off
set LOG=C:\diskpart.log
echo Execute diskpart script on %DATE% %TIME% > %LOG%
diskpart /s C:\diskpart.input.txt 1>>%LOG%

有时需要在运行时才确定要执行的 diskpart 指令,我们可以通过脚本动态生成指令文件:

@echo off
set X=%TEMP%\diskpart.input
1>%X% (
  echo select vdisk file="..."
  echo attach vdisk
  echo select partition 1
  echo assign letter=...
  echo exit
)
diskpart /s %X%
del %X%

上面的“1>%X%”是输出重定向。1是标准输出,因此这段程序是将标准输出写入到%X%这个文件中,之后调用diskpart /s 来执行这个文件。

也可以不使用临时文件来调用diskpart,记得 Linux 下的管道操作吧?tar ... | gzip ...,通过管道,前面命令的输出会作为后面命令的输入。我们可以使用管道操作来调用diskpart,比如:

echo select vdisk file="..." | diskpart

但问题是,一行echo输出给diskpart后,diskpart执行完就退出了,和后面的指令连接不起来。所以,我们需要将一批指令组合在一起,然后一起输出给diskpart:

@echo off
(
  echo select vdisk file="..."
  echo attach vdisk
  echo online disk noerr
  echo select partition 1
  echo assign letter=X
  echo exit
) | diskpart
可以通过组策略来控制这些脚本的执行,或是通过 windows 的计划任务来管理它们。


### 使用场景3:WinXP/Win2003

在 WinXP/Win2003,系统本身没有提供操作 vhd 的机制,不得不借助于第三方工具来实现。

对 vhd 的创建、分区等操作,交互方式的可以通过 DiskGenius 等工具来完成。通过程式来控制的,可使用 QEMU for windows 的 qemu-img。

对 vhd 的挂载操作则比较困难,你可以安装或提取 Virtual PC 中的 VHDMount,它应该可以满足这方面的要求,不过我没实际操作过。

如果 vhd 文件是固定大小(相对于动态扩展)的,那么还有一些其它方法来挂载 vhd,比如通过 imdisk 或 winvblock 来挂载。

imdisk 是一个很小巧的工具,可以创建内存盘,可以挂载很多种硬盘镜像,可惜没有好的图形界面。你可以在这儿下载 imdisk: http://www.ltr-data.se/opencode.html/

imdisk -a -f <vhd file> -m <挂载路径> -v 1

上面的参数 -v 1 表示挂载第一个分区。

如果你知道 vhd 中第一个分区的偏移量,那么也可以指定这个偏移量来挂载。比如我的vhd文件都是按1M对齐来分区的,所以我可以这样挂载: imdisk -a -f <vhd file> -b 1m -m <挂载路径>

如果你的系统中装了winvblock 的话,也可以使用它自带的一个小工具来挂载固定大小的vhd:

winvblk -cmd attach -u <vhd file> -m <挂载盘符>


Chen-Zhiqiang

Chen-Zhiqiang

粉丝 11
博文 23
码字总数 22936
作品 0
苏州
程序员
私信 提问
加载中
请先登录后再评论。
树莓派(Raspberry Pi):完美的家用服务器

自从树莓派发布后,所有在互联网上的网站为此激动人心的设备提供了很多有趣和具有挑战性的使用方法。虽然这些想法都很棒,但树莓派( RPi )最明显却又是最不吸引人的用处是:创建你的完美家用...

异次元
2013/11/09
5.8K
8
游戏开发者后端服务--OpenKit

OpenFeint 关门大吉后,OpenFeint 创始人推出了开源项目 OpenKit。OpenKit 支持Unity 3D游戏引擎,并未 iOS 和 Android 的游戏开发者提供开源 API以及存储、数据同步服务。OpenKit 目前提供對...

匿名
2013/03/11
2.9K
0
图形化的 IDE--LiveCode

LiveCode是一个图形化的IDE,允许用户通过拖放控件并编写代码,来创建桌面或移动应用程序(支持Windows、Mac OS、Linux、iOS和Android平台)。LiveCode受苹果HyperCard的启发,采用一种基于英...

匿名
2013/04/12
7.1K
0
样式化 iOS 应用--NUI

NUI 可以让你通过一个样式表对 iOS 应用进行外观定制,类似 CSS。你能创建在多个应用中重用的样式,而且使用规则类似 CSS,例如设置 ButtonBorderColor 为 #CCCCCC,或者使用变量 @primaryFo...

匿名
2012/12/04
8.7K
1
高效率的nio框架--nio java raptor

设计初衷是提供方便易用,且高效率的nio框架,一部分实现上参考了mina。还包括线程池,编解码,内存池等机制,以便于开发高性能tcp程序。 文档后续会慢慢的补上。 整体实现上尽量少的使用锁,...

齐楠
2012/12/12
3.3K
0

没有更多内容

加载失败,请刷新页面

加载更多

代理服务器和反向代理服务器之间有什么区别? - What's the difference between proxy server and reverse proxy server?

问题: 代理服务器和反向代理服务器有什么区别? 解决方案: 参考一: https://stackoom.com/question/wRc/代理服务器和反向代理服务器之间有什么区别 参考二: https://oldbug.net/q/wRc/W...

技术盛宴
今天
16
0
第八讲:配置外界可以访问虚拟机里面的HDFS

本节通过配置实现外界访问虚拟机Centos6.4里面的HDFS。为后续的java读写HDFS做准备 步骤有: 1、修改主机Windos7的网络配置 2、修改虚拟机Centos6.4里面的网络配置 3、修改虚拟机Centos6.4里...

刘日辉
今天
26
0
OSChina 周四乱弹 —— 不劳而获的饭好吃么?好吃!非常好吃!

Osc乱弹歌单(2020)请戳(这里) 【今日歌曲】 小小编辑推荐:《世界上不存在的歌 (2020重唱版)》- 陈奕迅 《世界上不存在的歌 (2020重唱版)》- 陈奕迅 手机党少年们想听歌,请使劲儿戳(这...

小小编辑
今天
31
3
从 GPU、TPU,到 Web 端、移动端,深度学习框架部署训练开始变简单

本文作者:o****0 早些时候的统计显示,今年3月,深度学习框架集中爆发。5月,有人发布可以直接在 iphone11上训练神经网络的开源项目。日前,百度开源国内首个可直接运行在 Web 端的深度学习...

百度开发者中心
昨天
16
0
如何从Git存储库中删除文件? - How can I delete a file from a Git repository?

问题: I have added a file named "file1.txt" to a Git repository. 我已将名为"file1.txt"的文件添加到Git存储库中。 After that, I committed it, added a couple of directories called......

富含淀粉
今天
31
0

没有更多内容

加载失败,请刷新页面

加载更多

返回顶部
顶部