磁盘格式化是计算机用户经常使用的操作之一,但由于操作系统的控制台和外壳(Shell)提供了对格式化的完美支持,使编程人员很容易忽视用户对格式化的
基本需求。在他们看来,磁盘格式化对用户来说并不是一个太大的问题,应用程序不必要对它提供支持。其实,这是一个错觉,当用户在运行应用程序遇到需要格式
化磁盘时,再切换到控制台或者资源管理器去格式化磁盘是非常不便和烦琐的。
还有一部分编程人员认为磁盘格式化很容易实现,没有技术障碍,因此没有赋予足够重视。其实,在实际编程时笔者发现磁盘格式化是一个不大不小的问题。一方
面,它要求编程尽量简单,不要涉及中断、端口读写、物理扇区存取、VXD、WDM驱动程序等复杂细节,只要能实现格式化即可,代码越简单越好,最好是只调
用一个函数即可实现。另一方面,笔者却发现,基本上所有的编程参考书籍都对这个问题只字不提,在MSDN中也很难找到一个具有这样功能的
FormatDisk函数。当然,我们可以利用WinExec、CreateProcess和ShellExecute等函数去执行Format命令,并
且这方案完全可行,不过随之产生的控制台窗口会使我们的窗口程序显得不伦不类,破坏原有的程序界面。虽然我们还可以通过设置CreateProcess函
数的参数实现对控制台窗口的隐藏,使Format.exe隐蔽地在后台运行,但这又需要我们维护它的完整路径,这也存在一定困难。
主要函数
从实际应用的角度看,从Windows 9X到Windows
NT都应该提供这个FormatDisk函数,否则怎么实现资源管理器窗口的磁盘格式化呢?笔者通过仔细查找发现,Windows
确实提供了这样一个函数,尽管文档资料没有注明,但是如果我们使用View
Dependencies打开Shell2.dll,就会发现这个函数。它就是SHFormatDrive,编译连接到Shell32.lib。尽管通过
平台的SDK文档和SHELLAPI.H文件并不能发现这个函数,但是Win32各个操作系统都能找到它的踪影。应用程序可以通过调用这个函数实现借用外
壳的磁盘格式化对话框格式化磁盘。调用约定如下:
DWORD WINAPI SHFormatDrive(HWND hwnd,UINT drive,UINT fmtID,UINT options);
参数含义如下:
hwnd:拥有对话框的窗口句柄,注意hwnd为NULL时,并不会导致这个对话框生成一个上层的应用程序,也就是说,这个参数总是非NULL,这个对话框只能作为一个窗口的子窗口,而不能作为一个单独的应用程序;
drive:要格式化的驱动器号,以A: == 0为基准,依此类推;
fmtID:必须设定为 SHFMT_ID_DEFAULT,即0xFFFF;
options:可以有两个选择项:SHFMT_OPT_FULL 0x0001和SHFMT_OPT_SYSONLY 0x0002,如果这一项设置为零,系统就要使用快速格式化作为默认设置。
该函数的返回值要么为一个下列以SHFMT_开头的值,要么是一个成功格式化的磁盘标识。
//上次格式化出错,磁盘可能被格式化
#define SHFMT_ERROR 0xFFFFFFFFL
//格式化被取消
#define SHFMT_CANCEL 0xFFFFFFFEL
// 不能进行磁盘格式化
#define SHFMT_NOFORMAT 0xFFFFFFFDL
实现步骤
1.函数接口声明
typedef DWORD (WINAPI *PFNSHFORMATDRIVE)(HWND hwnd,UINT drive,UINT fmtID,UINT options);
2.加载Shell32.dll库
HINSTANCE hInstance=LoadLibrary(_T
(“Shell32.dll”));
If(hInstance==NULL) return;
3.获得函数指针
PFNSHFORMATDRIVE pFnSHFormatDrive=(
PFNSHFORMATDRIVE)GetProcessAddress(_T
(“SHFormatDrive”));
if(pFnSHFormatDrive==NULL)
{
FreeLibrary(hInstance);
return;
}
4.调用函数
(pFnSHFormatDrive)(hwnd,drive/*a:==0*/,fmtID/* SHFMT_ID_DEFAULT */,options);
5.释放句柄资源
FreeLibrary(hInstance);
Return;
本程序在Windows 2000环境下调试通过,使用Delphi、Visual Basic的用户通过调用上述Windows SDK 函数也可以实现磁盘格式化。
- #if !defined(SHFMT_OPT_FULL)
-
-
#if defined (__cplusplus)
-
extern "C " {
-
#endif
-
-
/*****************************************************************
-
The SHFormatDrive API provides access to the Shell 's format
-
dialog box. This allows applications that want to format disks to bring
-
up the same dialog box that the Shell uses for disk formatting.
-
-
PARAMETERS
-
hwnd = The window handle of the window that will own the
-
dialog. NOTE that hwnd == NULL does not cause this
-
dialog to come up as a "top level application "
-
window. This parameter should always be non-null,
-
this dialog box is only designed to be the child of
-
another window, not a stand-alone application.
-
-
drive = The 0 based (A: == 0) drive number of the drive
-
to format.
-
-
fmtID = Currently must be set to SHFMT_ID_DEFAULT.
-
-
options = There are currently only two option bits defined.
-
-
SHFMT_OPT_FULL
-
SHFMT_OPT_SYSONLY
-
-
SHFMT_OPT_FULL specifies that the "Quick Format "
-
setting should be cleared by default. If the user
-
leaves the "Quick Format " setting cleared, then a
-
full format will be applied (this is useful for
-
users that detect "unformatted " disks and want
-
to bring up the format dialog box).
-
-
If options is set to zero (0), then the "Quick Format "
-
setting is set by default. In addition, if the user leaves
-
it set, a quick format is performed. Under Windows NT 4.0,
-
this flag is ignored and the "Quick Format " box is always
-
checked when the dialog box first appears. The user can
-
still change it. This is by design.
-
-
The SHFMT_OPT_SYSONLY initializes the dialog to
-
default to just sys the disk.
-
-
All other bits are reserved for future expansion
-
and must be 0.
-
-
Please note that this is a bit field and not a
-
value, treat it accordingly.
-
-
RETURN
-
The return is either one of the SHFMT_* values, or if
-
the returned DWORD value is not == to one of these
-
values, then the return is the physical format ID of the
-
last successful format. The LOWORD of this value can be
-
passed on subsequent calls as the fmtID parameter to
-
"format the same type you did last time ".
-
-
*****************************************************************/
-
DWORD WINAPI SHFormatDrive(HWND hwnd,
-
UINT drive,
-
UINT fmtID,
-
UINT options);
-
-
//
-
// Special value of fmtID which means "use the defaultformat "
-
//
-
-
#define SHFMT_ID_DEFAULT 0xFFFF
-
-
//
-
// Option bits for options parameter
-
//
-
-
#define SHFMT_OPT_FULL 0x0001
-
#define SHFMT_OPT_SYSONLY 0x0002
-
-
//
-
// Special return values. PLEASE NOTE that these are DWORD values.
-
//
-
-
#define SHFMT_ERROR 0xFFFFFFFFL // Error on last format,
-
// drive may be formatable
-
#define SHFMT_CANCEL 0xFFFFFFFEL // Last format wascanceled
-
#define SHFMT_NOFORMAT 0xFFFFFFFDL // Drive is not formatable
-
-
#if defined (__cplusplus)
-
}
-
#endif
-
#endif
-
-
//End:Begin
-
调用方式如:
-
SHFormatDrive (m_hWnd, 0 /* A: */, SHFMT_ID_DEFAULT, 0);
-
-
注意:
-
-
如果你不希望系统弹出Abort, Retry, or Ignore的询问对话框,可以用SetErrorMode
-
为(!SEM_FAILCRITICALERRORS),如下:
-
-
UINT OldMode = SetErrorMode(0); //得到缺省设置
-
SetErrorMode(OldMode & !SEM_FAILCRITICALERRORS);//设置处理方式
-
-
SHFormatDrive (m_hWnd, 0 /* A: */, SHFMT_ID_DEFAULT, 0);
-
-
SetErrorMode(OldMode);
阅读(1366) | 评论(0) | 转发(1) |