我的地盘我做主
2009年02月12日设计代码

没有评论
28 views

关于Environ函数

我们经常接触的获取路径的API有GetWindowsDirectory()、GetSystemDirectory(),但是还有一个API叫SHGetFolderPath很少有人用,它可获取的系统路径更多,例如:
Option Explicit

Private Const MAX_PATH = 260

‘Return Values
Private Const S_FALSE = &H1
Private Const E_INVALIDARG = &H80070057

‘Flags
Private Const SHGFP_TYPE_CURRENT = 0 ‘ current value for user, verify it exists
Private Const SHGFP_TYPE_DEFAULT = 1 ‘ default value, may not exist

‘nFolder Value
Private Const CSIDL_DESKTOP = &H0 ‘
Private Const CSIDL_INTERNET = &H1 ‘ Internet Explorer (icon on desktop)
Private Const CSIDL_PROGRAMS = &H2 ‘ Start Menu\Programs
Private Const CSIDL_CONTROLS = &H3 ‘ My Computer\Control Panel
Private Const CSIDL_PRINTERS = &H4 ‘ My Computer\Printers
Private Const CSIDL_PERSONAL = &H5 ‘ My Documents
Private Const CSIDL_FAVORITES = &H6 ‘ \Favorites
Private Const CSIDL_STARTUP = &H7 ‘ Start Menu\Programs\Startup
Private Const CSIDL_RECENT = &H8 ‘ \Recent
Private Const CSIDL_SENDTO = &H9 ‘ \SendTo 继续阅读 »

reg命令使用详解

编辑注册表不当可能会严重损坏您的系统。在更改注册表之前,应备份计算机上任何有价值的数据。
只有在别无选择的情况下,才直接编辑注册表。注册表编辑器会忽略标准的安全措施,从而使得这些设置

会降低性能、破坏系统,甚至要求用

户重新安装 Windows。可以利用“控制面板”或“Microsoft 管理控制台 (MMC)”中的程序安全更改多数

注册表设置。如果必须直接编辑注册表,则请首先将其备份。

使用 Reg 直接编辑本地或远程计算机的注册表。这些更改有可能造成计算机无法操作并需要重新安装操

作系统。所以不要直接编辑注册表,而

应尽可能利用“控制面板”或“Microsoft 管理控制台 (MMC)”更改注册表。
有些操作可以查看或配置本地或远程计算机的注册表项,而另外一些则只允许配置本地计算机的注册表设

置。同时,远程访问注册表也可能会

限制用于某操作的参数。请检查每个操作的语法以便验证该操作可以用于远程计算机,以及验证可用于那

种情况下的参数。

reg命令是WindowsXP提供的,它可以添加、更改和显示注册表项中的注册表子项信息和值。

reg add 继续阅读 »

2008年10月7日设计代码

没有评论
16 views

让Real Player从你的电脑走开

近自己用VB编写一个播放RM格式的影音文件播放器,打包后,兴冲冲的拿到朋友那去,结果老是报告“超出内存”。我倒!原来朋友的机器上没有装上Real Player,大跌脸面!急忙到网上查找关于Real Player的文章,结果一无所获!

看来只有俺亲自动手了!后来经过俺几天N2次的安装和卸载,外加方便面与白开水!终于让Real Player从电脑中走开!

准备工作:查看系统进程的软件(如Winodws优化大师的进程管理,它可将每个软件所引用的进程全部列出,让你一览无余!)、Real Player、豪杰超级DVD2.1 。

安装Real Player后,你会发现在Program Files\Common Files根目录下有一个Real目录下,里面分别有Codecs、Common、Plugins、Update、Visualizations子目录,里面都是一些动态链接文件,这个可是Real Player的核心力量

打开豪杰的的安装目录,你会发现在豪杰的安装目录下也有Codecs、Common、Plugins比较一下,你就会发现这几个目录中的文件,全是与Program Files\Common Files相对应目录中的文件啊!

让我们打开豪杰来播放一个RM格式的文件,然后打开Winodws优化大师的进程管理(当然用其它查看进程也可以),发现豪杰在引用Program Files\Common Files\Real目录下的文件

发现了这个秘密,说明我们只要能够明白豪杰的大概原理,就可以做出既使客户端没有Real Player也同样如豪杰那样播放RM格式的影音文件了!

打开注册表,在[HKEY_LOCAL_MACHINE\Software\CLASSES\Software\]和[HKEY_CLASSES_ROOT\ CLASSES\Software\]分支下都有名为RealNetworks的项(这分支下RealNetworks里面的内容是完全一样,唯一不同的是它们的支名),当我们卸载Real Player,Real Player就会删除RealNetworks项。这时再用豪杰来播放RM文件,我们就会发现豪杰就会在上述两分支重建RealNetworks项(即使你再次手动删除,当你用豪杰播放RM文件时豪杰,它就会又重建RealNetworks项)。
导出[HKEY_LOCAL_MACHINE\Software\CLASSES\Software\RealNetworks]分支.最好先删除这一分支后,在打开豪杰播放RM文件,让豪杰来重建RealNetworks。因为豪杰引用较少的文件就能播放,而Real Player引用的较复杂,没有必要去浪费资源!

在导出文件中有以下三项内容:(假设豪杰安装在D盘) [HKEY_LOCAL_MACHINE\Software\CLASSES\Software\RealNetworks\Prefe_rences\DT_Common]
@="D:\\HEROSOFT\\HERO2001\\Common\\"(是引用豪杰Common目录)
[HKEY_LOCAL_MACHINE\Software\CLASSES\Software\RealNetworks\Prefe_rences\DT_Plugins]
@="D:\\HEROSOFT\\HERO2001\\Plugins\\"(是引用豪杰Plugins目录)
[HKEY_LOCAL_MACHINE\Software\CLASSES\Software\RealNetworks\Prefe_rences\DT_Codecs]
@="D:\\HEROSOFT\\HERO2001\\Codecs\\"(是引用豪杰Codecs目录)
从导出文件剪切以上三项与下面两项合并成一个注册表文件,这样导出文件的剩余部分即为公用部分(无论是Real Player还是豪杰都必不可小的)。

[HKEY_LOCAL_MACHINE\SOFTWARE\Classes\Software\RealNetworks\Update\6.0\Preferen_ces\Components\RMACore:6.0\File17]
@="D:\\Windows\\System\\pncrt.dll"(引用pncrt.dll)
[HKEY_LOCAL_MACHINE\SOFTWARE\Classes\Software\RealNetworks\RealPlayer\6.0\Pref_erences\DataTypes\rpmOCX\OCXDLL]
@="D:\\Windows\\System\\rmoc3260.dll"(引用rmoc3260.dll)
这样新合成的注册表文件,可根据你文件所在目录随意修改(即5处下画线处),只要你愿意,你可以将这些文件藏在你电脑的任意一个角落里!而公用部分导入注册表后就不用问它了!
注意事项:导出的注册表会因为操作系统不同导出的形式略有不同,因为WINDOWS 98是采用16位注册表编辑器,而WINDOWS 2000以上的是基于32位注册表编辑器。但它们所导出的内容是完全一样的!
这样就大功告成了!干快试试吧!让你的程序没有Real Plyaer一样干活!
( 此方法在WINDOWS 98 / 2000 / 2000 Server / XP均可通过!)

delphi:QQ自动发消息源码

这里面有的到窗口句柄,输入框句柄和按钮句柄的方法!
你可以结合使用的到你想的到的功能!
这是一个qq自动发送的功能,你看看,应该有点用吧!:)
[code]
procedure TForm1.Button1Click(Sender: TObject);
var
hParent,hButton,hMemo: HWND;
begin
Memo1.CopyToClipboard;//把Memo中选中的语句拷贝到剪贴板中
try
//找发送消息的QQ窗口
hParent := FindWindow(nil, '发送消息');
//然后找回话时用的编辑窗口,Point函数用于返回一个TPoint类型变量
hMemo := ChildWindowFromPointEx(hParent, Point(50, 100), CWP_ALL);
//找到“送讯息”按钮的句柄
hButton := FindWindowEx(hParent,0,nil,'送讯息(&S)');
if (hParent = 0) or (hMemo = 0) or (hButton = 0) then
MessageBox(Handle,'没有找到发送窗口,请重试!','错误',MB_ICONWARNING)
else
begin
//向发送消息中的回话编辑框发送粘贴消息
SendMessage(hMemo,WM_PASTE,0,0);
//向“送讯息”按钮送单击消息以模仿按键发送回话
SendMessage(hButton,BM_CLICK,0,0);
end;
except
//如果发生以外错误给出提示
MessageBox(Handle,'发送消息出错,请重试!','错误',MB_ICONWARNING);
end;
end;

[/code]

Shockwaveflash 资料收集1

AlignMode(int型)和SAlign(WideString型) 控制动画的显示位置(把这两个属性列在一起说明它们是相互

关联的,改变一个另一个也会相应地改变,以下类似)。取值范围及含义如下:
   0 空 当前位置
   1 L 当前位置靠左
   2 R 当前位置靠右
   3 LR 当前位置居中
   4 T 当前位置靠上
   5 LT 左上
   6 TR 右上
   7 LTR 上方居中
   8 B 当前位置靠下
   9 LB 左下
   10 RB 右下
   11 LRB 下方居中
   12 TB 当前位置垂直居中
   13 LTB 靠左垂直居中
   14 TRB 靠右垂直居中
   15 LTRB 中央位置
  【属性】BackgroundColor(int型)和BGColor(WideString型) 设置背景颜色,BackgroundColor为整

型值,BGColor为它的HEX字符串。
  【属性】Loop(bool型) 是否循环显示
  【属性】Menu(bool型) 是否显示右键菜单,建议设为true,因为它可以完成对Flash动画的大部分控

制工作,而不用我们写代码。
  【属性】Movie(WideString型) Flash动画的文件名,可以在运行状态动态设置,要关闭一个动画只

要把它设为空即可。
  【属性】Quality(int型)和Quality2(WideString型) 控制动画的显示质量,一般将Quality设为1以获

得高质量的显示效果。
  【属性】ScaleMode(int型)和scale(WideString型) 控制动画的显示比例,取值范围及含义如下:
   0 ShowAll 显示全部
   1 NoBorder 无边框模式
   2 ExactFit 拉伸到整个画面
   3 空 原始大小

【方法】PercentLoaded 返回动画已经加载的百分比,你可以建立一个进程条(ProgressBar)来显示
动画加载的进程。
  【方法】LoadMovie 用于加载网络上的动画,动画文件名为一个BSTR型的URL值,在 C++ Builder
中可以用 AnsiToOLESTR 函数将Char型的字符串转换成BSTR型。
  好了,利用上面介绍的属性和方法,相信你已经很好地使用它了!遗憾的是 ShockWaveFlash 控件
功能现在
还不太完善,比如无法返回动画的实际大小和背景颜色等,但对于我们只要在程序中显示一个特定的
Flash动画来说,这些并不重要。

*************************************************************************************************

tshockwaveflash主要属性如下:

readystate:读一个flash文件时的状态,其中包括0=loading、1=uninitialized、2=loaded、

3=interactive和4=complete;
totalframes:总帧数,只有当readystate = 4时才能访问该属性;
framenum:当前播放的帧;
playing:播放或暂停一个flash;
quality:指定当前渲染的质量,包括0=low, 1=high、2=autolow、3=autohigh;
scalemode:缩放模式,0=showall、1= noborder、2 = exactfit;
alignmode:对齐模式,left=+1、right=+2、=+4、bottom=+8;
backgroundcolor:背景色,-1为默认颜色;
loop:是否循环;
movie:指定播放的flash文件路径,可以为一个url。

tshockwaveflash主要方法如下:

play():开始播放动画;
stop();停止播放动画;
back();播放前一帧动画;
forward():播放后一帧动画;
rewind():播放第一帧动画;
setzoomrect(int left, int top, int right, int bottom):设置缩放的区域;
zoom(int percent):按百分比缩放;
pan(int x, int y, int mode):缩放播放面板,其中模式0为按像数、1为按窗口百分比。

tshockwaveflash主要事件如下:

onprogress(int percent):读取一个flash时触发;
onreadystatechange(int state):状态改变时触发。states的值可以为0=loading、

1=uninitialized、2=loaded、3=interactive和4=complete。
****************************************************************************************
用VB编写FLASH动画播放器_VisualBasic教程
Flash4是MacroMedia公司出品的矢量动画创作专业软件,利用该软件制作的矢量动画具有文件体积小、带

音效和兼容性好等特点。那么,你想不想在自己编写的程序中加入Flash动画,为自己的程序添加一道亮

丽的色彩呢?
  一、编程原理
  本程序利用了Flash4本身自带播放Flash动画的控件Swflash.ocx。你可以通过以下途径获得该控件:

1、安装Flash4;2、安装Windows98自带的Flash插件,方法:依次单击“开始”菜单-“设置”-“控制面板”

-“添加/删除程序”-“Windows安装程序”-“多媒体”-“详细资料”-选中“MacromediaShockwaveFlash”前

的复选框确定即可。以上方法都会将该控件安装到Windows目录下的System\Macromed\Flash子目录下。
  二、示例程序
  下面就是一个用Swflash.ocx控件编写的Flash动画播放器。本程序可一次打开多个Flash动画文件,

并可在播放过程中选择播放打开的文件、随时改变播放质量、画面大小等状态;在播放过程中可以随时对

播放的当前帧数进行调整或者手动进行逐帧播放,在状态栏里有当前播放状态的相关说明。在实现以上功

能时,几乎用全了Swflash.ocx控件的主要属性、方法。
  编程过程如下:
  1、窗体、界面设计。
  新建工程,选择“工程”菜单下的“部件”命令,在“部件”窗口的“控件”列表中将“Shockwaveflash”、

“MicrosoftCommonDialogControl6.0(SP3)”、“MicrosoftWindowsCommonControl6.0(SP3)”前的复选框选

中,然后确定。再在窗体中分别加入1个CommonDialog控件、1个Slider控件、3个Label控件、6个

CommandButton控件和1个StatusBar控件。其中:
  将Form1的“Caption”属性设置为:Flash动画播放器。这是控制窗口。
  将CommonDialog1的CancelError设置为True,DialogTitle设置为“打开Flash动画文件”,Filter属性

设置为“Flash动画(*.swf)|*.swf|”,FilterIndex设置为1,MaxFileSize设置为10240。
  将Slider1的SelectRanger的属性设置为“True”,SmallChange属性和LargeChange属性设置为10,

TickFrequengcy属性设置为20,TextPosition设置为“1-SldBelowRight”。
  将Label(1-3)分别放在Slider1下的左端、中间和右端。其中,Label1的Caption设置为“0帧”,

Label2和Label3的Caption设置为空字符串。
  6个CommandButton的“名称”属性分别为:cmdOpen、cmdPlay、cmdPause、cmdPre、cmdPreFrame、

cmdNextFrame、cmdNext、cmdExit,“Caption”属性分别为:打开、播放、暂停、上一个、上一帧、下一

帧、下一个、退出。
  在StatusBar上单击鼠标右键,选择“属性”,从弹出的窗口中选择“窗格”页面,用鼠标点击“插入窗格

”5次,在索引1-5中分别设置“文本”属性为:“共打开了0个文件”、“状态:”、“等待”、“帧数:”、“0”,

再适当设置每一项的“最小宽度”的属性(可参考图1中的比例)。
    进入菜单编辑器(按快捷键Ctrl+E)。设置第一个菜单标题为“显示控制”,名称为:

mnuDisplay;在“显示控制”下设立子菜单标题分别为“全部显示”、“随窗口大小变化”、“缩放至窗口大小”

,名称分别为:mnuDisplay0、mnuDisplay1、mnuDisplay2。设置第二个菜单标题为“质量控制”,名称为

:mnuQuality;在“质量控制”下设立子菜单标题分别为“低分辨率”、“高分辨率”,名称分别为:

mnuQuality0、mnuQuality1。设置第三个菜单标题为“播放控制”,名称为:mnuPlayControl;在“播放控

制”下设立子菜单标题分别为“循环播放”、“放大画面”、“缩小画面”,名称分别为:mnuLoopPlay、

mnuZoomIn、mnuZoomOut。
  选择“工程”菜单下的“添加窗体”命令,新增一个窗体Form2作为播放窗口。在Form2上加入1个

ShockwaveFlash控件和1个Timer控件。将Timer1控件的“Interval”属性设置为“20”。
  最后,对各窗体、控件的大小、位置进行适当的调整,其大小、位置可参考图1。
  2、程序代码
  第一步:在Form1的代码窗口中添加以下代码:
  DimFileNames()AsString注释:用于保存打开的文件名称。
  DimPlayFileNumAsInteger注释:用于计算正在播放的文件序号。
  DimTotalFileAsInteger注释:用于统计打开的文件总数。
  PrivateSubcmdOpen_Click()注释:打开
  OnErrorGoToExitOpen
  CommonDialog1.Flags=cdlOFNAllowMultiselectOrcdlOFNFileMustExistOrcdlOFNExplorer
  CommonDialog1.FileName=″"
  CommonDialog1.ShowOpen注释:显示“打开”对话框。
  注释:以vbNullChar作为子字符串的边界分隔字符串CommonDialog1返回的FileName。
  FileNames()=Split(CommonDialog1.FileName,vbNullChar)
  IfUBound(FileNames)=0Then注释:用户只打开了一个文件。
  Form2!ShockwaveFlash1.Movie=FileNames(0)
  TotalFile=1
  PlayFileNum=0
  Else注释:用户打开了多于一个文件。
  Form2!ShockwaveFlash1.Movie=FileNames(0)+″\″+FileNames(1)
  TotalFile=UBound(FileNames)
  PlayFileNum=1
  EndIf
  StatusBar1.Panels(1).Text=″共打开了″+Trim(Str(TotalFile))+″个文件″
  cmdPlay_Click
  ExitOpen:
  EndSub
  PrivateSubcmdPlay_Click()注释:开始播放
  IfTotalFile<1ThenExitSub注释:用户还没有打开文件。
  注释:显示Form2开始播放动画。
  Form2.Caption=FileNames(PlayFileNum)+″-Flash动画播放器″
  Form2.Show
  Form2!ShockwaveFlash1.Playing=True
  IfTotalFile=1ThenPlayFileNum=0
  注释:显示状态条的信息。
  StatusBar1.Panels(3).Text=″正在播放文件:″+FileNames(PlayFileNum)+″...″
  注释:显示滑动条的状态。
  Slider1.Max=Form2!ShockwaveFlash1.TotalFrames
  Label2.Caption=Str(Slider1.Max/2)+″帧″
  Label3.Caption=Str(Slider1.Max)+″帧″
  EndSub
  PrivateSubcmdPause_Click()注释:暂停播放
  Form2!ShockwaveFlash1.Stop
  EndSub
  PrivateSubcmdPre_Click()注释:播放上一个文件
  IfTotalFile<>1Then注释:当用户打开多于一个文件时
  PlayFileNum=PlayFileNum-1
  IfPlayFileNum<1ThenPlayFileNum=TotalFile
  Form2!ShockwaveFlash1.Movie=FileNames(0)+″\″+FileNames(PlayFileNum)
  EndIf
  注释:显示播放状态的信息。
  StatusBar1.Panels(3).Text=″正在播放文件:″+FileNames(PlayFileNum)+″...″
  Slider1.Max=Form2!ShockwaveFlash1.TotalFrames
  Form2.Caption=FileNames(PlayFileNum)+″-Flash动画播放器″
  Label2.Caption=Str(Slider1.Max/2)+″帧″
  Label3.Caption=Str(Slider1.Max)+″帧″
  EndSub
  PrivateSubcmdNext_Click()注释:播放下一个文件
  IfTotalFile<>1Then注释:用户打开多于一个文件时
  PlayFileNum=PlayFileNum+1
  IfPlayFileNum>TotalFileThenPlayFileNum=1
  Form2!ShockwaveFlash1.Movie=FileNames(0)+″\″+FileNames(PlayFileNum)
  EndIf
  注释:显示播放状态的信息。
  StatusBar1.Panels(3).Text=″正在播放文件:″+FileNames(PlayFileNum)+″…″
  Slider1.Max=Form2!ShockwaveFlash1.TotalFrames
  Form2.Caption=FileNames(PlayFileNum)+″-Flash动画播放器″
  Label2.Caption=Str(Slider1.Max/2)+″帧″
  Label3.Caption=Str(Slider1.Max)+″帧″
  EndSub
  PrivateSubcmdPreFrame_Click()注释:跳到动画的上一帧
  Form2!ShockwaveFlash1.Back
  EndSub
  PrivateSubcmdNextFrame_Click()注释:跳到动画的下一帧
  Form2!ShockwaveFlash1.Forward
  EndSub
  PrivateSubcmdExit_Click()注释:退出程序
  End
  EndSub
  PrivateSubSlider1_Scroll()
  注释:当用户拖动滑动条时,将播放帧数设置为滑动条中的值。
  Form2!ShockwaveFlash1.FrameNum=Slider1.Value
  EndSub
  PrivateSubmnuDisplay0_Click()
  注释:将画面大小设置为在控件内保持动画原来比例全部显示
  Form2!ShockwaveFlash1.ScaleMode=0
  mnuDisplay0.Checked=True
  mnuDisplay1.Checked=False
  mnuDisplay2.Checked=False
  EndSub
  PrivateSubmnuDisplay1_Click()
  注释:将画面的缩放设置为随控件横向(或纵向)的缩放而变化
  Form2!ShockwaveFlash1.ScaleMode=1
  mnuDisplay0.Checked=False
  mnuDisplay1.Checked=True
  mnuDisplay2.Checked=False
  EndSub
  PrivateSubmnuDisplay2_Click()
  注释:将画面大小设置为不理会动画原来比例缩放至控件大小
  Form2!ShockwaveFlash1.ScaleMode=2
  mnuDisplay0.Checked=False
  mnuDisplay1.Checked=False
  mnuDisplay2.Checked=True
  EndSub
  PrivateSubmnuLoopPlay_Click()
  注释:将播放方式设置为循环或不循环。
  mnuLoopPlay.Checked=NotmnuLoopPlay.Checked
  Form2!ShockwaveFlash1.Loop=NotForm2!ShockwaveFlash1.Loop
  EndSub
  PrivateSubmnuQuality0_Click()
  注释:将画面质量设置为低分辨率
  Form2!ShockwaveFlash1.Quality=0
  mnuQuality0.Checked=True
  mnuQuality1.Checked=False
  EndSub
  PrivateSubmnuQuality1_Click()
  注释:将画面质量设置为高分辨率
  Form2!ShockwaveFlash1.Quality=1
  mnuQuality0.Checked=False
  mnuQuality1.Checked=True
  EndSub
  PrivateSubmnuZoomIn_Click()
  注释:放大画面。
  Form2!ShockwaveFlash1.Zoom(50)
  EndSub
  PrivateSubmnuZoomOut_Click()
  注释:缩小画面。
  Form2!ShockwaveFlash1.Zoom(200)
  EndSub
  PrivateSubForm_Unload(CancelAsInteger)
  End注释:结束程序
  EndSub
  第二步:在Form2的代码窗口中添加以下代码:
  PrivateSubForm_Resize()
  注释:将ShockwaveFlash1控件的大小设置为Form2的大小。
  ShockwaveFlash1.Top=Form2.ScaleTop
  ShockwaveFlash1.Left=Form2.ScaleLeft
  ShockwaveFlash1.Width=Form2.ScaleWidth
  ShockwaveFlash1.Height=Form2.ScaleHeight
  EndSub
  PrivateSubTimer1_Timer()
  注释:在状态栏和滑动条上显示当前播放的帧。
  Form1!StatusBar1.Panels(5).Text=Str(ShockwaveFlash1.FrameNum)
  Form1!Slider1.Value=ShockwaveFlash1.FrameNum
  EndSub
  第三步:调试、运行程序,运行界面如图2所示。
  当播放Flash动画时,在播放窗口中单击鼠标右键时,将会弹出如图3所示的菜单。在该菜单,我们可

以完成控制Flash动画播放的大部份工作。若想取消该功能,只要将Shockwaveflash控件的Menu属性设置

为False即可。
  以上程序在Windows98,VB6.0下运行通过。->

2008年09月20日设计代码

3条评论
90 views

delphi虚拟点击过360安全卫士

360安全卫士总是会提示有某个程序要添加到随机启动里面,让用户来确定是不是要让这个程序成为随机启动.只要我们能快速的点击那个"确定"也能让木马成功的添加到随机启动里面. 首先我们应该了解这两个函数,findwindow和findwindowex她们是API函数,在VB语言里面我们要在写很常的声明,用的时候也容易出错,但是在delphi中由于VCL的封装这两个API函数可以像DELPHI自身的函数那样简单调用来获得窗体句柄。FindWindow(LPCTSTR LpClassName,LPCTSTR LpWindowName);
LpClassName :指向一个指定了类名的空结束字符串,或一个标识类名字符串的成员的指针。如果该参数为一个成员,则它必须为前次调用theGlobafAddAtom函数产生的全局成员。该成员为16位,必须位于IpClassName的低 16位,高位必须为 0。

LpWindowName:指向一个指定了窗口名(窗口标题)的空结束字符串。如果该参数为空,则为所有窗口全匹配

FindWindowEx(HWND hwndParent,HWND hwndChildAfter,LPCTSTR lpszClass,LPCTSTR lpszWindow);

hwndParent:要查找子窗口的父窗口句柄。

如果hwnjParent为NULL,则函数以桌面窗口为父窗口,查找桌面窗口的所有子窗口。

hwndChildAfter :子窗口句柄。查找从在Z序中的下一个子窗口开始。子窗口必须为hwndPareRt窗口的直接子窗口而非后代窗口。如果HwndChildAfter为NULL,查找从hwndParent的第一个子窗口开始。如果hwndParent 和 hwndChildAfter同时为NULL,则函数查找所有的顶层窗口及消息窗口。

lpszClass:指向一个指定了类名的空结束字符串,或一个标识类名字符串的成员的指针。如果该参数为一个成员,则它必须为前次调用theGlobaIAddAtom函数产生的全局成员。该成员为16位,必须位于lpClassName的低16位,高位必须为0。

lpszWindow:指向一个指定了窗口名(窗口标题)的空结束字符串。如果该参数为 NULL,则为所有窗口全匹配。返回值:如果函数成功,返回值为具有指定类名和窗口名的窗口句柄。如果函数失败,返回值为NULL

了解这两个函数后我们就开始进行编程。

在窗体上加个timer1控件并把interval的值设为小于500大于0

procedure TForm1.Timer1Timer(Sender: TObject);
var
idid,hand,he:thandle;
begin
idid:=findwindow('Afx:400000:0',nil);//获取360安全卫士的提示句柄
IF idid <> 0 THEN//当获得360安全卫士句柄的时候
begin
hand:=findwindowex(idid,0,'Button','允许此动作');//先获取"允许此动作"的选项句柄
if hand<>0 then//获得"允许此动作"的句柄
begin
postmessage(hand,wm_lbuttondown,0,0);
postmessage(hand,wm_lbuttonup,0,0);//将选项确定在允许此动作上
he:=findwindowex(idid,0,'Button','确定');//获得"确定"的句柄
postmessage(he,wm_lbuttondown,0,0);
postmessage(he,wm_lbuttonup,0,0);//自动点击确定
end;
end;
end;

end.

这样我们就将我们成功的将"木马"添加到随机起动里面了.

2008年09月18日设计代码

没有评论
12 views

QQ聊天记录是如何加密的

QQ,就是OICQ,TENCENT公司研发的即时信息软件,是中国市场上国产IM软件绝对的老大。中国网民几乎人手至少一个QQ号码。大家都比我清楚,不多介绍。

本文谈谈QQ的安全问题。

QQ具有如此惊人的人气,却有着与之不相称的安全问题。基本上可以说,使用QQ,基本没有任何隐私可言!另外它也为你的电脑带来了诸多附送的安全隐患。有识之士如我都早已不用QQ啦。

一,本地密码保存方式

QQ的客户端会不经用户同意,把用户的密码经过数万次的MD5运算后存在本地。每次登陆在发送网络数据包之前进行本地验证,相信熟悉QQ的朋友对这一点都不陌生。这样事实上给了攻击者暴力破解QQ密码的机会,只要攻击者得到本地保存的这个数据即可。这个文件曾经叫ewh.db或者user.db,不知道现在是否又变了。说明一点,由于MD5作了数万次,这样的破解效率不高,但再低的效率也有弱智密码中招,当年在线尝试登陆都可以,还有什么不可能呢?
如果选择了自动登陆,那么密码的一次MD5保存在oicq2000.cfg中,破解速度大大提高。

二,本地聊天记录查看漏洞

典型的攻击场景是:已经拿到全部本地记录,就是一个以QQ号为名的文件夹,不知道密码(或者俗称忘记了密码,求助者多数号称是mm)如何查看其聊天记录?
QQ登陆的流程是这样的:1.输入用户名密码->2.本地验证通过->3.得到用户界面(企鹅开始闪动)->4.发送登陆包->5.收到登陆包成功响应->6.登陆成功。
其中在步骤3的时候,我们就可以查看聊天记录了。
如果2失败,则要求重新输入密码;如果5失败,则退出步骤3中得到的用户界面。对于没有正确密码的攻击者来说,要保持3的状态以查看本地聊天记录,需要首先骗过2,并防止4发生。由于QQ没有软件加密(加壳),所以2十分容易,修改一个跳转就OK。4就更容易了,拔了网线或设置防火墙就可以了。现在网上有很多这样的修改教程和修改好的客户端。所以不再赘述。

三,本地聊天记录的加密方法

事实上以上第二条所说是一个利用已有客户端简单规避本地检查的办法。如果你愿意,可以自己写一个查看聊天记录的工具,因为它的加密方式是如此的脆弱。
首先普及一点常识:TEA算法(Tiny Encryption Algorithm,即微型加密算法)是一个正规的密码学意义上的加密算法,你可以在http://www.ftp.cl.cam.ac.uk/ftp/papers/djw-rmn/djw-rmn-tea.html找到原作者对其的介绍。QQ的加密,包括本地文件加密和远程数据包加密,主要使用的就是这个算法。值得注意的是原作者使用的是32轮运算(即使是32轮,这个算法也被证明是可以已知明文攻击的),然而TENCENT将其降为了16轮。时间上省了一半,但安全性却严重下降。算法常识以后再讲,我们只要知道该算法是公开的就可以了。(废话,不公开哪来的那么多开源QQ,比如lumaQQ)。
QQ本地历史数据,包括聊天记录和一些日志,用一个key加密后存在本地Msg.db或者MsgEx.db中,但是这个key呢,用QQ号码的MD5加密存在本地同一个文件中,换句话说,知道QQ号码就可以解密这些文件,QQ号码是什么呢?就是所在目录名!
当然,如果你启用了本地消息加密,情况会稍微好那么一点点,要看你的本地加密密码强度了。但是有多少人会去设置呢?

四,木马泛滥,Windows的HOOK

关于QQ密码的安全性我想是大家最关心的问题。网络上充斥着各种各样的偷QQ密码的文章或者工具,其实绝大多数越来越不好用,有些所谓偷密码的工具甚至本身就是木马,是来偷你自己的密码的。这些工具主要原理是挂钩子,判断当前窗口名,截键盘,某种方式发回。实际上,能种下木马本身已经是可遇而不可求的了。加上对方稍有安全意识,有个象样点的防火墙,这些工具就很难成功。
另外臭名昭著的QQ病毒之一类,俗称QQ尾巴的,也多是利用这种原理,查找窗口,发送消息。
针对这些问题,TENCENT公司自己也做了不少工作,比如窗口名是空的,实际看到的窗口名是画上去的。比如软键盘,比如其他的密码保护措施,可惜效果不太好啊。

五,登陆数据包如果遭窃听,密码可能被离线暴力破解

这是一个十分严重的问题,也会导致密码丢失。而且比前一条所说更严重。实际上,攻击者不再需要装木马,他只要会用Sniffer就可以了。
随便分析一下QQ的程序,或者看看开源的QQ程序,我们就知道,虽然普通数据包是协商的密钥,但QQ的登陆请求数据包中,由于还没有协商密钥,临时密钥是写在数据段之前的,也就是说这个数据包是可以轻松解密的。那么这个数据包里包含什么呢?它包含了用QQ密码的MD5或2次MD5加密空字符串得到的一段16字节数据!加密算法是TEA,最要命的是,经过TENCENT公司对算法模式的一个包装,如果用一个不相干的密钥去尝试解密这段二进制数据,解密函数会返回错误!而不是解密出一段无用的数据并返回正确!这种傻瓜逻辑为穷举攻击创造了极大的便利条件。实际攻击者不需要去穷举128位的密钥,他只要猜测可能的密码,做MD5运算一到二次后尝用来尝试解密那16字节数据就可以了。
简而言之,如果你的密码够简单,或者进了字典,那么恶意攻击者只要用一个sniffer,或者开个QQ代理,就能知道你的密码,这个穷举只要本地运算即可,而且速度非常之快。大约10^6~10^8次/秒。这个速度意味着,所有8位以下数字,6位以下字母,简单数字字母组合的密码都是形同虚设。作为对策,建议普通用户使用足够强壮的密码并且不要使用任何QQ代理。

六,得到工作密钥,实时解密QQ数据

QQ聊天数据加密用了协商密钥作工作密钥,这不错。可是,它竟然用对称算法传递协商的密钥!?
QQ的工作密钥是服务器随机生成并发回的(也许不是随机?可以预测?不过我没搞到QQ服务器源码,不知道),如果QQ在线,这个密钥会是一直不变的,如果不在线一段时间,这个工作密钥就被更新。所以每两次登陆,如果间隔了一定时间,大约十几分钟,这个密钥就不同。从而一劳永逸地破解工作密钥是不现实的。但是如果有了QQ密码的MD5,那么攻击者可以解密QQ登陆确认数据包,解密后竟然就可以看到工作密钥,是16个字节的大小写字母加数字组合。此后所有客户端到服务器的数据将全部用此工作密钥解密。如果需要点对点聊天,那么所需密钥用同样算法和工作密钥加密送来。总之,此后所有QQ数据都可以认为是明文了。
如果你的密码被偷或被破解,攻击者很可能不通知你,也不修改你的密码,因为他知道你有密码保护,但是不要以为你的QQ号没有丢,可能攻击者正在看着你的聊天信息偷着乐呢。他也随时可以上线踢你下去,帮你聊天。

七,太多而繁杂的发行版本

QQ的客户端有太多的版本了,各种语言发行版不论,各种年号版、XP版、beta版、正式发行版,冠以各色名字,令人眼花缭乱,关键是他们还都好用。实际上,一个成功的C/S结构的网络产品不应当同时有太多的客户端版本,不仅难以维护,增大服务器开销,而且给冒名版本提供了可乘之机。现在流行有许多非官方发布的QQ客户端版本,什么珊瑚虫版,免广告版,显IP版……都大行其道,傻瓜也会想得到,其中必然有偷密码版,恶作剧版,留后门版在其中鱼目混珠。QQ对自己的客户端不加壳也就算了,它还不作进程检查和文件完整性校验,也没有守护进程。这么大大咧咧,怎么对得起这么多信之爱之的忠实用户啊?

八,多处不作任何加密处理的模块

也许由于数据量太大,语音和视频聊天就都没有加密,是明文传播,任何人可以直接在线收听收看。如果你想用WEB方式登陆www.qq.com,那么密码也就按照明文发出去了。

九,乱添插件,乱加功能

直接调用控件编写的内置IE浏览器,完全继承了IE的各种功能,以及漏洞。大家知道IE的漏洞研究的人十分之多,那么QQ也就随之非常危险了。
QQ秀,Q币,手机绑定等等在线服务,常常是每推出一个,就捎带出一堆漏洞。研究的人不少,这个需要在线研究,有风险,所以我没怎么干过。谁有经验告诉我啊。
自定义头像漏洞:据说QQ自定义头像的功能传出过一个漏洞,导致任意代码执行,我虽然没有实践过,但想来可能不假。
可以想见,功能越多,潜在的危险也就越大!这其实是安全软件开发中一条很有名的原则。所以建议各位,尽量少去玩试用版新功能,使用稳定而功能少的旧版本其实有时利大于弊。

十,相同认证方式的其他网络服务和产品

HTTP服务,《凯旋》游戏,QQ游戏大厅,等等,都可以用QQ号加同样的密码登陆。也许方便了用户,但在安全性上来讲这是大忌。整体安全性降到了其中的最小值。凯旋和游戏大厅是有客户端的,用户名密码的加密方式与QQ相同。但是HTTP可是明文的啊。

以下讲几个场景。

例如:
首先,滑稽的很,我竟然可以在http://service.qq.com查询到任意QQ号是否申请了密码保护,那么查查隔壁mm的吧。
然后,晓之以情动之以理,mm你去申请密码保护吧。同时打开sniffer。
哎,申请密码保护竟然要WEB方式输入密码!你知道么?申请密码保护的过程可能就是丢失密码的过程哦,顺便还捎带了提示问题及其答案呢!

再例如:
我是网管,已经得到了你的密码,我修改了你的密码,你没有密码保护,那么你可以去申诉,向一个CGI叫做http://service.qq.com/cgi-bin/TellError的申诉。
然后,我就知道了你的曾经密码,真实信息,另一个QQ号……真是大丰收啊。什么,你打电话申诉?好吧去打吧,很艰辛的,社会工程学攻击已经超出本篇的范围了。

再例如,你有密码保护,好吧那么你的找回过程还是要WEB登陆。再说,现在有多少电子邮箱又能抵挡住sniffer这样的简单工具呢?我就不多说了。
下面我们来欣赏一下QQ的解密代码。
[code]
void decrypt_qword(unsigned long *in, unsigned long *key, unsigned long *out)
{

unsigned long code[4];
register unsigned long i=16, j=0xe3779B90, m, n;

m = swapu32(in[0]);
n = swapu32(in[1]);

code[0] = swapu32(key[0]); code[1] = swapu32(key[1]);
code[2] = swapu32(key[2]); code[3] = swapu32(key[3]);

while(i-- >0)
{
n -= ((m>>5)+code[3])^((m<<4)+code[2])^(j+m);
m -= ((n>>5)+code[1])^((n<<4)+code[0])^(j+n);
j += 0x61C88647;
}
out[0] = swapu32(m);
out[1] = swapu32(n);
}

int decrypt_msg(unsigned char *in, int inlen, unsigned long *key,
unsigned char *out, unsigned long *outlen)
{
unsigned char q[8], mkey[8], *q1, *q2, *outp;
register int count, i, j, p;

if (inlen%8 || inlen<16) return 0;
decrypt_qword((unsigned long *)in, key, (unsigned long *)q);
j = q[0]&0x7;
count = inlen - j - 10;
// if (*outlen < count || count < 0) return 0; //?????*outlen
if (count < 0) return 0;
*outlen = count;

memset(mkey, 0, 8);
q2 = mkey;
i = 8; p = 1;
q1 = in+8;
j ++;
while (p <= 2) {
if (j < 8) {
j ++;
p ++;
} else if (j == 8) {
q2 = in;
for (j = 0; j < 8; j ++ ) {
if (i + j >= inlen) return 0;
q[j] ^= q1[j];
}
decrypt_qword((unsigned long *)q, key, (unsigned long *)
q);
i += 8;
q1 += 8;
j = 0;
}
}
outp = out;
while(count !=0) {
if (j < 8) {
outp[0] = q2[j] ^ q[j];
outp ++;
count --;
j ++;
} else if (j == 8) {
q2 = q1-8;
for (j = 0; j < 8; j ++ ) {
if (i + j >= inlen) return 0;
q[j] ^= q1[j];
}
decrypt_qword((unsigned long *)q, key, (unsigned long *)
q);
i += 8;
q1 += 8;
j = 0;
}
}
for (p = 1; p < 8; p ++) {
if (j < 8) {
if (q2[j]^q[j])
return 0;
j ++;
} else if (j == 8 ) {
q2 = q1;
for (j = 0; j < 8; j ++ ) {
if (i + j >= inlen) return 0;
q[j] ^= q1[j];
}
decrypt_qword((unsigned long *)q, key, (unsigned long *)
q);
i += 8;
q1 += 8;
j = 0;
}
}
return 1;
}

[/code]
算法模式简要概括如下:
F(i) = P(i) + C(i-1)
C(i) = E(Fi) + F(i-1)
P是明文,C是密文,E是TEA算法,作用于8字节单元上。每次i增加1,就作用于一个8字节分组。

我们看到QQ的加密在算法模式上作了两个设计,其一引入随机字符作头部padding,这样基本保证同样的明文和密钥可以导致完全不同的加密结果。模式设计使得解密函数解密后可以准确抛弃掉这部分随机字。这个设计的确很好。但其模式在另一点上做的太差了,就是用返回值明确指出了解密的成功与否。

实际上至少两年前,水木清华的Crack版上,pure(青衣~ shadow in silence) 的文章就揭示了这一段代码,早已不是什么秘密了。我自己也跟踪得到了这样的东西,不过还是参考过Shufeng Tan的Net-OICQ-0.8,以及Puzzlebird为Gaim写的QQ插件OpenQ-0.3.1,至于lumaQQ就没看了,想来也就差不多了吧。

事实上我还有一个猜想,32轮的TEA降低到16轮,肯定是出奇地危险,如果对算法破解有兴趣,那么可以看看下面这些参考书。
1)John Kelsey,Bruce Schneier, David Wagner, “Related Cryptanalysis of 3-Way, Biham-DES, CAST, DES-X, NewDES, RC2, and TEA”
2)Fauzan Mirza, “Block Ciphers And Cryptanalysis”
3)VIKRAM REDDY ANDEM, “A CRYPTANALYSIS OF THE TINY ENCRYPTION ALGORITHM”

2007年01月29日设计代码

没有评论
32 views

delphi李维专栏\3D游戏编程入门\3D游戏开发大全 站点

delphi 李维专栏

http://www.delphifans.com/SoftList/Catalog_12_SoftTime_Desc_1.html

3D游戏编程入门经典

http://book.csdn.net/bookfiles/199/

3D游戏开发大全

http://book.csdn.net/bookfiles/27/index.html

Delphi 3D 网: http://www.delphi3d.net/index.php

主要有OPENGL和Didirect这两种,还有就是使用第三方的3D开发包。。。

DELPHI MD5加密算法

具体使用方法如下,另外还附有源代码:
/*
1、 MD5String、MD5File、MD5Print、MD5Match这四个函数是供调用的。其他是用来辅助这几个函数的子函数。
2、MD5String为加密字符串。
3、MD5File为加密这个文件。
4、MD5Print是将加密后的密文转换成字符串。
5、MD5Match是用来比较密文是否一致。

加密字符串aaa MD5String('aaa')
将加密后的aaa显示出来 MD5Print(MD5String('aaa'))
比较两次密文是否一致: MD5Match(MD5String('第一次明文'),MD5String('第二次输入的明文'))
*/

MD5加密算法(DELPHI)

unit md5;

delphi ADO 连接参数

[SqlServer 连接]
//连接Sqlserver上的数据库
ADOCon.ConnectionString := 'Provider=SQLOLEDB.1;'+
'Password=密码;'+
'Persist Security Info=True;'+
'User ID=用户名;'+
'Initial Catalog=数据库名;'+
'Data Source=服务器地址或域名';

[Access 连接]
//读取运行程序当前目录下\data\wlgs.mdb Access数据库文件.
ADOCon.ConnectionString := 'Provider=Microsoft.Jet.OLEDB.4.0;Data Source='+
ExtractFilePath(Application.ExeName)+
'Data\wlgs.mdb'+
';Persist Security Info=False';

返回顶部