看到论坛好多人问win7下写注册表的问题,我结合自己的理解写了一点东西,首先声明一下,本人初学Delphi,水平有限,大家见笑了,有什么不对之处请老鸟多指点。

[背景]
win7/Vista提供的UAC机制,是win7/Vista的新增功能之一。它的主要目的是防止对于操作系统本身的恶意修改。如果想对于win7/Vista的系统设置进行改动,必须通过UAC的验证才能够进行。通过这样的手段,大大提供了系统的安全性。关于UAC的利弊,网络上的说法褒贬不一,在这里就不具体讨论了。

[应用]
Delphi写的程序一般都可以在win7/vista上运行,但是有关注册表、程序文件夹的操作会无声的失效,这给普通用户带来很大不便,他们并不明白什么时候程序需要写注册表(因为没有提示),需要以管理员身份运行程序!现在大多数Delphier还是停留在D7的阶段,这时候一般大家都会把责任推给D7,是D7太老了,不支持Win7/Vista! 在试了D2007后,发现依然不行,于是感慨说Delphi对win7/vista支持不好,事实真是这样吗?

打开D2007(sorry,现在机子上没用以后的版本,我想应该相同)的目录:\source\Win32\vcl,找到winxp.pas这个单元,用记事本打开发现它引用了winxp.rc, 再用记事本打开windows.rc, 发现它编译的是 sample.manifest 这个文件,用记事本打开它,看到是用xml这样描述的:

<?xml version="1.0" encoding="UTF-8" standalone="yes"?>

<assembly xmlns="urn:schemas-microsoft-com:asm.v1" manifestVersion="1.0">
<assemblyIdentity
type="win32"
name="DelphiApplication"
version="1.0.0.0"
processorArchitecture="*"/>
<dependency>
<dependentAssembly>
<assemblyIdentity
type="win32"
name="Microsoft.Windows.Common-Controls"
version="6.0.0.0"
publicKeyToken="6595b64144ccf1df"
language="*"
processorArchitecture="*"/>
</dependentAssembly>
</dependency>
<trustInfo xmlns="urn:schemas-microsoft-com:asm.v3">
<security>
<requestedPrivileges>
<requestedExecutionLevel
level="asInvoker"
uiAccess="false"/>
</requestedPrivileges>
</security>
</trustInfo>
</assembly>

对比D7相同的文件,发现多了<trustInfo>项的,这也就是所谓的支持UAC的关键,查阅msdn有关VC2008的manifes的设置,有关权限的说明如下:

<security>
<requestedPrivileges>
<requestedExecutionLevel level="asInvoker" uiAccess="false"/>
</requestedPrivileges>
</security>

这里要注意的是requestedExecution Level的值,一般用asInvoker或requireAdministrator,普通的程序应该用asInvoker来执行,意思是按照目前你登陆win7/Vista帐号的权限执行,requireAdministrator顾名思义就是需要你启动管理员权限才能执行。这里是win7/Vista会不会跳出UAC提示窗口的重点。
1)如果用asInvoker应该就不会再提示了,我觉得这是个鸡肋!因为win7/vista默认是不以administrator登陆的,登陆的帐号根本没有太多权限!你的程序如果操作了注册表、程序文件夹的话当然在这个帐号下会无声的失效;
2)在VC2008中,程序中如果没有manifest,则默认为requireAdministrator权限(爽呀!),requestedExecutionLevel为 requireAdministrator的可执行文件前面都会有一个小盾牌提醒使用者。好了,看到这里,大家应该明白了吧!

[解决方法]
对于D7,解决方法太简单了。如果你操作了注册表之类的“危险地带”的话,就要使用这个来提醒你的用户要以管理员权限运行,其实这个网上早就有了,我又拷过来了:)
1.建立 res 文件
建立一个文本文件,名字可以自己起,我这里叫:UAC.manifest,内容:

<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
<assembly xmlns="urn:schemas-microsoft-com:asm.v1" 
manifestVersion="1.0"> 
<trustInfo xmlns="urn:schemas-microsoft-com:asm.v3">
<security>
<requestedPrivileges>
<requestedExecutionLevel level="requireAdministrator"/>
</requestedPrivileges>
</security>
</trustInfo>
</assembly>

建立文本文件,名为 UAC.rc,内容:

1 24 UAC.manifest

编译成 uac.res 文件,运行:

brcc32 uac.rc -fouac.res

2.在代码中引入
打开项目文件,加入
{$R uac.res}

3.编译程序

或者你还可以仿照xpman.pas写个VistaUAc.pas,其中引用以上资源,编译后将相应的dcu拷入lib文件夹,vistUac.pas拷入vcl文件夹,需要时,你可以在工程或单元中像引用xpman一样方便地uses VistaUac!

对于D2007(sorry,以后的版本没有试,因为本机没装,应该也一样)有些麻烦,因为它默认是启用所谓的Runtime themes的,以上uac.res是没办法正常引用的,解决方法有两种:1)关闭runtime themes才能正常引用, 但程序没有xp特效了,郁闷了吧!2)用D7的winxp.res,xpman.pas覆盖D2007的,重新编译D7的xpman.pas生成的dcu覆盖2007的(建议备份!), 当需要编写修改“危险地带”程序时,放弃使用runtime themes,转而uses xpman和引用以上资源,程序xp特效又回来了,久违的小盾也出现了!

PS:用Dejoy 的D7lite7.3里的winxp.res不行,因为他已经改过了,内容和D2007的是一模一样的,不能和uac.res 共存!

[结论]
以上解决方法并非是非完美的,UAC的提示或多或少给用户带来了不安全的感觉,最好的方法应该由程序本身和用户交互说明需要使用管理员权限运行,或者自己你像在xp以下系统上一样,自己提高权运行权限,实现一些操作,但这样做并非现实,MS能会让它的辛苦研发出的UAC项目形同虚设?MS最终的想法可能是要大家都向它申请数字签名。

以上有什么不对之处,请指正。

[写在最后]
Borland及CG真的太好了,每次更新都巴不得把大家项目中所用的控件全提供了,以致于现在倒像是个制作控件的公司,每次基本都是几个控件升级,编译器很少改动!授之以鱼不如授之以渔,Delphi让很多人养成了一种习惯,遇到问题先去想有没有什么控件可以实现,有的人编程就是用VCL控件堆积木,还到处挑VCL的bug,真是深在福中不知福呀!源代码都给你了,你不会学着改吗?你要是用用VC,好多都要从头做起,编程好像是直接在用api(程序当然执行效率高了,可真没效率),MFC不是真正面向对象,写个界面能把人急疯了,你会真觉得Delphi太好了!可人家MS也知道自己家的东西烂,编了庞大的MSDN让它的程序员模仿,有如老师亲临,大大给他的用户壮了胆,也给了他们创造了更广阔的想象空间... 扯远了,大家见笑了!

参考:http://m.blog.csdn.net/blog/fghydx/35218457

Delphi在win7/vista下写注册表等需要管理员权限的解决方案的更多相关文章

  1. delphi在64位系统下写注册表注意事项

    HKEY_LOCAL_MACHINE写这个主键下的项,在64位系统下可能会重定向,所以构造时要加KEY_WOW64_64KEY reg := TRegistry.Create(KEY_WRITE or ...

  2. Win7,Vista UAC下应用程序标注为“需要管理员权限”的四种方法(可以修改注册表)

    [转]Vista UAC下应用程序标注为“需要管理员权限”的四种方法 在Microsoft 的UACBlog里对此有过叙述.总结如下: 首先,如果一个程序被识别为管理员程序时,Vista会在它的图标上 ...

  3. win7 64bit+vs2010 操作注册表

    注册表五个根键 HKEY_CLASSES_ROOT--管理文件系统  HKEY_LOCAL_MACHINE--管理当前系统硬件配置  HKEY_LOCAL_USER--管理系统当前用户配置  HKEY ...

  4. VB6之写注册表

    难免会遇到写注册表的情况,写了个实用点的RegWrite函数.为了减少代码量,用WScript.Shell取代了API来实现. 使用方式就在注释中了,就不再过多解释了.PS:注释比实现代码要丰富多了, ...

  5. IE 内使用ActiveX,写注册表被重定向到如下注册表

    IE 内使用ActiveX,写注册表被重定向到如下注册表,所以使用注册表做标记要注意下,目前还没找为什么会这样 HKEY_CURRENT_USER\Software\Microsoft\Interne ...

  6. C++写注册表

    1.       注册表简介 注册表是为Windows NT和Windows95中所有32位硬件/驱动和32位应用程序设计的数据文件,用于存储系统和应用程序的设置信息.16位驱动在Winnt (Win ...

  7. WinCE下读取注册表获得SD路径

    WinCE下读取注册表获得SD路径 [要点]WinCE注册表中[HKEY_LOCAL_MACHINE\System\StorageManager\Profiles\SDMemory\] 下键Folde ...

  8. Java Windows下读取注册表的工具类

    import java.io.BufferedReader; import java.io.IOException; import java.io.InputStreamReader; import ...

  9. 系统开启UAC情形下开机自启动程序如何以管理员权限启动

    系统开启UAC情形下开机自启动程序如何以管理员权限启动 题记:本文阐述的是在Windows系统开启UAC的情况下,开机自启动程序需要以管理员权限启动, 系统弹出UAC对话框,用户同意的情形下启动程序 ...

随机推荐

  1. 关于js中return false、event.preventDefault()和event.stopPropagation()

    在平时项目中,如果遇到需要阻止浏览器默认行为,大家经常会用return false;和event.preventDefault()来阻止,但对它俩的区别还是有些一知半解,于是看了文档,查了些资料,在此 ...

  2. Windows PowerShell:管理服务器

    一.概述 Cmdlets 用于服务器的管理方面主要体现在4个方面:服务.日志.进程.服务器管理器. 1.服务 •  Get-Service.查看某个服务的属性. •  New-Service.创建一个 ...

  3. python 内置函数和表达式

    对于简单的函数来说,可以使用类似于三元运算来表示,即: lambda表达式 格式: lambda [arg1[, arg2, ... argN]]: expression   先来看看三元表达式 #普 ...

  4. JS1 js获取dom元素方法

     js获取dom元素方法  1.通过ID选取元素(getElementById) 1)使用方法:document.getElementById("domId")         其 ...

  5. 使用 C# 编程对RTF文档的支持

    http://www.68design.net/Development/Aspnet/Basis-AspNet/26011-1.html

  6. [Json] C#ConvertJson|List转成Json|对象|集合|DataSet|DataTable|DataReader转成Json (转载)

    点击下载 ConvertJson.rar 本类实现了 C#ConvertJson|List转成Json|对象|集合|DataSet|DataTable|DataReader转成Json|等功能大家先预 ...

  7. NPOI的使用

    简介:NPOI是POI(APATCH的一个开源项目)项目的.NET版本,最初的POI只用于JAVA来操作EXCEL or WORD等微软OLE2组件项目.使用NPOI可以完成在你没有安装Office或 ...

  8. maven 创建的符号连接命令

    E:\Joyplus\src\main\webapp\WEB-INF>mklink /d lib ..\..\..\.\..\target\ediHelperSuite-0.5\WEB-INF\ ...

  9. java静态代理,动态代理,cglib代理

    代理模式在我们的应用中是很常见的,例如拦截器,spring的事务管理等.之所以能被代理,是因为java允许我们通过反射机制动态构造目标对象,并调用相应的方法. 就好像拿到了目标对象的引用,自然可以在目 ...

  10. 【感悟】看Hyouka的感想 (1)

    最近偶然从B站看到了<冰菓>这个(个人觉得是推理)番   我突然觉得自己曾经做的一些行为欠妥   有才能者的不自知,是对无才能者的讽刺   举个例子就是:即当别人说你很牛的时候,你却说你只 ...