斑竹求救,过路朋友看看

wxjh 2002-10-22 08:07:09
现在一个有一个机房管理系统,(我不知道他的源代码),当时间到时自动关机,操作系统为98,我写了一个小程序,阻止系统关机,如下:在自己的机子上试时,我的程序运行时无法可以阻止使用“开始“菜单里的关机命令,但是,我放到装有这个管理系统的机子上时,机子照关不误,不只是何原因;?请大家帮助;我的程序运行时释放在系统托盘中的。
我使用了如下的消息处理过程
...........
procedure closemsg(var msg:TMessage); message wm_queryendsession;
..........
procedure Tform1.closemms;
begin
msg.wparam:=0;
msg.lparam:=........//这里没问题,只是我没记住,是win32sdk中的
end;
...全文
82 50 打赏 收藏 转发到动态 举报
写回复
用AI写文章
50 条回复
切换为时间正序
请发表友善的回复…
发表回复
wxjh 2002-10-25
  • 打赏
  • 举报
回复
先结贴子 ,我在另开几分贴子,答谢各位!!!
wxjh 2002-10-25
  • 打赏
  • 举报
回复
: cg1120(代码最优化-§志不强者智不达§)
昨天没有好好看你的代码,今天回去好好研究一下,你这是把系统的关机函数进行替换,应该没问题,谢谢了。。。。。。。
Billy_Chen28 2002-10-25
  • 打赏
  • 举报
回复
强制关机是不会发送wm_queryendssion消息的,只能用我上面的拦截API函数的方法,wxjh(苦儿),你看看吧
wxjh 2002-10-25
  • 打赏
  • 举报
回复
问题搞定了,用消息钩子函数,我将接受到的wm_queryendssion消息用我的消息进行替换,然后给系统回送假的返回值,跳过了那个软件的条件判断语句,使他认定系统已经关机,不再发送强制关机命令,但是我却没有解决强制关机消息的拦截,只能说是投机取巧而已,请继续关注。。。。。我将另开一帖
fangchangjiang 2002-10-24
  • 打赏
  • 举报
回复
up
Billy_Chen28 2002-10-24
  • 打赏
  • 举报
回复
把函数ExitWindows和ExitWindowsEx换成自己定义的函数即可,我帮你做一个程序试试
Billy_Chen28 2002-10-24
  • 打赏
  • 举报
回复
现在只能拦截API函数ExitWindows和ExitWindowsEx,具体的可参考以下文章:
http://www.delphibbs.com/delphibbs/dispq.asp?lid=887904
wxjh 2002-10-24
  • 打赏
  • 举报
回复
wxjh2001@163.com
wxjh 2002-10-24
  • 打赏
  • 举报
回复
昨天看了window.pas单元,中间有个api函数是setwineventhook,但是我看了msdn,里面讲的很少,不知道这个函数能、不能钩到关机事件呢?
wxjh 2002-10-24
  • 打赏
  • 举报
回复
昨天看了window.pas单元,中间有个api函数是setwineventhook,但是我看了msdn,里面讲的很少,不知道这个函数能、不能钩到关机事件呢?
naughtyboy 2002-10-24
  • 打赏
  • 举报
回复
网吧没有工具,回去看看能不能将消息拦截下来
naughtyboy 2002-10-24
  • 打赏
  • 举报
回复
用GetWindow和GetWindowText的到程序主窗体的Caption
PostMessage(FindWindow(nil,windowcaption),WM_CLOSE,0,0);
(没办法跟踪,提前把程序给他消灭掉看看)
Billy_Chen28 2002-10-24
  • 打赏
  • 举报
回复
还有EWX_SHUTDOWN参数
Billy_Chen28 2002-10-24
  • 打赏
  • 举报
回复
如果的确是使用了EWX_FORCE参数,操作系统将不再广播WM_QUERYENDSESSION消息!现在只有写一个勾子,当勾到ExitWindows和ExitWindowsEx
函数时,屏蔽掉EWX_FORCE参数:)
ZHENG017 2002-10-24
  • 打赏
  • 举报
回复
找到其端口,并将其连接drop掉,到http://www.xici.net/main.asp?board=66545问一下.最厉害的(我认为哈)牛人shotgun的专栏.
Billy_Chen28 2002-10-24
  • 打赏
  • 举报
回复
老兄,你看懂了再说吧
wxjh 2002-10-24
  • 打赏
  • 举报
回复
exitwindows这个函数不是我的程序调用的,而是别人的程序的,我现在是要截取他发送的消息,也就是让它的强制关机无效
Billy_Chen28 2002-10-24
  • 打赏
  • 举报
回复
library MYAPIDLL;

{ Important note about DLL memory management: ShareMem must be the
first unit in your library's USES clause AND your project's (select
Project-View Source) USES clause if your DLL exports any procedures or
functions that pass strings as parameters or function results. This
applies to all strings passed to and from your DLL--even those that
are nested in records and classes. ShareMem is the interface unit to
the BORLNDMM.DLL shared memory manager, which must be deployed along
with your DLL. To avoid using BORLNDMM.DLL, pass string information
using PChar or ShortString parameters. }

uses
Windows,
WinSock,
SysUtils,
Classes,
HookAPI in '..\Borland\Delphi5\Projects\HookAPI.pas';

{$R *.RES}
type
TExitWindowsEx = function(Str: PAnsiChar): BOOL; stdcall;
TExitWindows = function(Str: PAnsiChar): BOOL; stdcall;
var
OldExitWindowsEx: TExitWindowsEx;
OldExitWindows: TExitWindows;
function MyExitWindowsEx(DC: HDC; X, Y: Integer; Str: PAnsiChar; Count: Integer): BOOL; stdcall;
begin
Result:=OldExitWindowsEx('xxx');
end;
function MyExitWindows(Str: PAnsiChar): BOOL; stdcall;
begin
Result:=OldExitWindows('xxx');
end;
begin
if @OldExitWindowsEx = nil then @OldExitWindowsEx := LocateFunctionAddress(@ExitWindowsEx);
if @OldExitWindows = nil then @OldExitWindows := LocateFunctionAddress(@ExitWindows);
RepointFunction(@OldExitWindowsEx, @MyExitWindowsEx);
RepointFunction(@OldExitWindows, @MyExitWindows);
end.
Billy_Chen28 2002-10-24
  • 打赏
  • 举报
回复
unit Demo;

interface

uses
Windows, Messages, SysUtils, Classes, Graphics, Controls, Forms, Dialogs,
StdCtrls, ExtCtrls, Menus;

type
TForm1 = class(TForm)
Button1: TButton;
Button2: TButton;
Label1: TLabel;
procedure Button1Click(Sender: TObject);
procedure Button2Click(Sender: TObject);
private
{ Private declarations }
public
{ Public declarations }
end;
procedure API_Hookup; stdcall; external 'MYAPIDLL.dll';
procedure API_HookDown; stdcall; external 'MYAPIDLL.dll';
var
Form1: TForm1;

implementation

{$R *.DFM}

procedure TForm1.Button1Click(Sender: TObject);
var
i:integer;
begin
API_Hookup;
Self.Repaint;
for i:=0 to self.ControlCount-1 do
begin
self.Controls[i].Refresh;
end;
end;

procedure TForm1.Button2Click(Sender: TObject);
var
i:integer;
begin
API_HookDown;
Self.Repaint;
for i:=0 to self.ControlCount-1 do
begin
self.Controls[i].Refresh;
end;
end;

end.

unit HookAPI;

interface

uses
Windows, Classes;
function LocateFunctionAddress(Code: Pointer): Pointer;
function RepointFunction(OldFunc, NewFunc: Pointer): Integer;

type //¶¨ÒåÒ»¸öÈë¿Ú½á¹¹
PImage_Import_Entry = ^Image_Import_Entry;
Image_Import_Entry = record
Characteristics: DWORD;
TimeDateStamp: DWORD;
MajorVersion: Word;
MinorVersion: Word;
Name: DWORD;
LookupTable: DWORD;
end;

type //¶¨ÒåÒ»¸öÌøתµÄ½á¹¹
TImportCode = packed record
JumpInstruction: Word; //¶¨ÒåÌøתָÁîjmp
AddressOfPointerToFunction: ^Pointer; //¶¨ÒåÒªÌøתµ½µÄº¯Êý
end;
PImportCode = ^TImportCode;
implementation

function LocateFunctionAddress(Code: Pointer): Pointer;
var
func: PImportCode;
begin
Result := Code;
if Code = nil then exit;
try
func := code;
if (func.JumpInstruction = $25FF) then
begin
Result := func.AddressOfPointerToFunction^;
end;
except
Result := nil;
end;
end;

function RepointFunction(OldFunc, NewFunc: Pointer): Integer;
var
IsDone: TList;
function RepointAddrInModule(hModule: THandle; OldFunc, NewFunc: Pointer): Integer;
var
Dos: PImageDosHeader;
NT: PImageNTHeaders;
ImportDesc: PImage_Import_Entry;
RVA: DWORD;
Func: ^Pointer;
DLL: string;
f: Pointer;
written: DWORD;
begin
Result := 0;
Dos := Pointer(hModule);
if IsDone.IndexOf(Dos) >= 0 then exit;
IsDone.Add(Dos);

OldFunc := LocateFunctionAddress(OldFunc);

if IsBadReadPtr(Dos, SizeOf(TImageDosHeader)) then exit;
if Dos.e_magic <> IMAGE_DOS_SIGNATURE then exit;
NT := Pointer(Integer(Dos) + dos._lfanew);

RVA := NT^.OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_IMPORT]
.VirtualAddress;

if RVA = 0 then exit;
ImportDesc := pointer(integer(Dos) + RVA);
while (ImportDesc^.Name <> 0) do
begin
DLL := PChar(Integer(Dos) + ImportDesc^.Name);
RepointAddrInModule(GetModuleHandle(PChar(DLL)), OldFunc, NewFunc);
Func := Pointer(Integer(DOS) + ImportDesc.LookupTable);
while Func^ <> nil do
begin
f := LocateFunctionAddress(Func^);
if f = OldFunc then
begin
WriteProcessMemory(GetCurrentProcess, Func, @NewFunc, 4, written);
if Written > 0 then Inc(Result);
end;
Inc(Func);
end;
Inc(ImportDesc);
end;
end;

begin
IsDone := TList.Create;
try
Result := RepointAddrInModule(GetModuleHandle(nil), OldFunc, NewFunc);
finally
IsDone.Free;
end;
end;

end.
ihihonline 2002-10-23
  • 打赏
  • 举报
回复
哇,解决了?
呵呵
http://www.nxrs.net/bbs/dispbbs.asp?boardID=1&ID=77
我给你回复了;
有时间的话,你再去看一看;
-----------------------------------------------------------
菜鸟论坛招斑竹;
www.nxrs.net/bbs
嘻嘻;
别用砖砸俺
加载更多回复(30)

1,183

社区成员

发帖
与我相关
我的任务
社区描述
Delphi Windows SDK/API
社区管理员
  • Windows SDK/API社区
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
暂无公告

试试用AI创作助手写篇文章吧