//from
http://ccrun.com/article/go.asp?i=653&d=b2m5o1uses ImageHlp;function GetDLLFileExports(
  szFileName: PChar;
  mStrings: TStrings
): Boolean;
var
  hFile: THANDLE;
  hFileMapping: THANDLE;
  lpFileBase: Pointer;
  pImg_DOS_Header: PImageDosHeader;
  pImg_NT_Header: PImageNtHeaders;
  pImg_Export_Dir: PImageExportDirectory;
  ppdwNames: ^PDWORD;
  szFunc: PChar;
  i: Integer;
begin
  Result := False;
  if not Assigned(mStrings) then Exit;
  hFile := CreateFile(szFileName, GENERIC_READ, FILE_SHARE_READ, nil,
    OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, 0);
  if(hFile = INVALID_HANDLE_VALUE) then Exit;
  hFileMapping := CreateFileMapping(hFile, nil, PAGE_READONLY, 0, 0, nil);
  if hFileMapping = 0 then
  begin
    CloseHandle(hFile);
    Exit;
  end;  lpFileBase := MapViewOfFile(hFileMapping, FILE_MAP_READ, 0, 0, 0);
  if lpFileBase = nil then
  begin
    CloseHandle(hFileMapping);
    CloseHandle(hFile);
    Exit;
  end;  pImg_DOS_Header := PImageDosHeader(lpFileBase);
  pImg_NT_Header := PImageNtHeaders(
    Integer(pImg_DOS_Header) + Integer(pImg_DOS_Header._lfanew));  if IsBadReadPtr(pImg_NT_Header, SizeOf(IMAGE_NT_HEADERS)) or
    (pImg_NT_Header.Signature <> IMAGE_NT_SIGNATURE) then
  begin
    UnmapViewOfFile(lpFileBase);
    CloseHandle(hFileMapping);
    CloseHandle(hFile);
    Exit;
  end;  pImg_Export_Dir := PImageExportDirectory(
    pImg_NT_Header.OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_EXPORT].
      VirtualAddress);
  if not Assigned(pImg_Export_Dir) then
  begin
    UnmapViewOfFile(lpFileBase);
    CloseHandle(hFileMapping);
    CloseHandle(hFile);
    Exit;
  end;
  // 63 63 72 75 6E 2E 63 6F 6D
  pImg_Export_Dir := PImageExportDirectory(
    ImageRvaToVa(pImg_NT_Header, pImg_DOS_Header, DWORD(pImg_Export_Dir),
    PImageSectionHeader(Pointer(nil)^)));  ppdwNames := Pointer(pImg_Export_Dir.AddressOfNames);  ppdwNames := Pointer(ImageRvaToVa(pImg_NT_Header, pImg_DOS_Header,
    DWORD(ppdwNames), PImageSectionHeader(Pointer(nil)^)));
  if not Assigned(ppdwNames) then
  begin
    UnmapViewOfFile(lpFileBase);
    CloseHandle(hFileMapping);
    CloseHandle(hFile);
    Exit;
  end;  for i := 0 to pImg_Export_Dir.NumberOfNames - 1 do
  begin
    szFunc := PChar(ImageRvaToVa(pImg_NT_Header, pImg_DOS_Header,
      DWORD(ppdwNames^), PImageSectionHeader(Pointer(nil)^)));
    mStrings.Add(szFunc);
    Inc(ppdwNames);
  end;
  UnmapViewOfFile(lpFileBase);
  CloseHandle(hFileMapping);
  CloseHandle(hFile);
  Result := True;
end;procedure TForm1.Button1Click(Sender: TObject);
begin
  GetDLLFileExports('C:\WINDOWS\SYSTEM32\MSSIP32.DLL', Memo1.Lines);
end;

解决方案 »

  1.   

    C++ -> delphi
    支持:_)
      

  2.   

    //使用如下代码搜索出闲置的方法
    uses TypInfo;procedure UnusedMethods(mComponent: TComponent; mStrings: TStrings);
    //设计 Zswang 2006-08-05 wjhu111#21cn.com 尊重作者,转贴请注明出处
    type
      PMethodInfo = ^TMethodInfo;
      TMethodInfo = packed record
        rSize: Word;
        rAddr: Pointer;
        rName: ShortString;
      end;type
      TMethodTable = packed record
        rCount: Word;
        rMethodInfo: array[0..0] of TMethodInfo;
      end;
      PMethodTable = ^TMethodTable;var
      vEventList: TList;  vMethodTable: PMethodTable;
      vMethodInfo: PMethodInfo;
      I: Integer;  procedure fScanEvent(mComponent: TComponent);
      var
        vPropList: PPropList;
        vPropCount: Integer;
        vMethod: TMethod;
        I: Integer;
      begin
        if not Assigned(mComponent) then Exit;
        vPropCount := GetPropList(mComponent, vPropList);
        for I := 0 to vPropCount - 1 do
          case vPropList[I].PropType^.Kind of
            tkMethod:
            begin
              vMethod := GetMethodProp(mComponent, vPropList[I].Name);
              if Assigned(vMethod.Code) then vEventList.Add(vMethod.Code);
            end;
          end;
        for I := 0 to mComponent.ComponentCount - 1 do
          fScanEvent(mComponent.Components[I]);
      end;
    begin
      if not Assigned(mStrings) or not Assigned(mComponent) then Exit;
      vEventList := TList.Create;
      mStrings.BeginUpdate;
      try
        mStrings.Clear;
        vMethodTable := PPointer(PChar(mComponent.ClassType) + vmtMethodTable)^;
        vMethodInfo := @vMethodTable^.rMethodInfo[0];
        fScanEvent(mComponent);
        for I := 0 to vMethodTable.rCount - 1 do
        begin
          if vEventList.IndexOf(vMethodInfo.rAddr) < 0 then
            mStrings.Add(vMethodInfo.rName);
          Inc(PChar(vMethodInfo), SizeOf(Word) + SizeOf(Pointer) + SizeOf(Byte) +
            Length(vMethodInfo^.rName));
        end;
      finally
        vEventList.Free;
        mStrings.EndUpdate;
      end;
    end;procedure TForm1.FormCreate(Sender: TObject);
    begin
      UnusedMethods(Self, Memo1.Lines); //输出结果
    end;
      

  3.   

    function FindBitmapPoint( //寻找子位图的位置
      mBitmapMain: TBitmap; //主位图
      mBitmapSub: TBitmap //子位图
    ): TPoint; //返回子图像存在的坐标,如不存在则返回(-1,-1)
    //设计 Zswang 2006-08-04 wjhu111#21cn.com 尊重作者,转贴请注明出处
    const
    //pfDevice, pf1bit, pf4bit, pf8bit, pf15bit, pf16bit, pf24bit, pf32bit, pfCustom
      cBitsPerPixels: array[TPixelFormat] of Byte = (0, 1, 4, 8, 15, 16, 24, 32, 0);
                           //像素格式所占用的字位数列表
    var
      I, J, K, L: Integer; //循环变量
      vStrMain: string; //主位图一行的像素数据字符串格式
      vStrSub: string; //子位图一行的像素数据字符串格式
      vLine: PChar; //临时ScanLine用
      vBytesSub: Integer; //子位图一行像素数据占用的字节数
      vBytesMain: Integer; //主位图一行像素数据占用的字节数
      vBitsPerPixels: Byte; //一个像素占用的字位数
      vFlag: Boolean;
    begin
      Result := Point(-1, -1);
      ///////Begin 安全判断
      if not Assigned(mBitmapMain) or not Assigned(mBitmapSub) then Exit;
      if mBitmapMain.PixelFormat <> mBitmapSub.PixelFormat then Exit;
      if (mBitmapSub.Height <= 0) or (mBitmapSub.Width <= 0) or
        (mBitmapMain.Height <= 0) or (mBitmapMain.Width <= 0) then Exit;
      ///////End 安全判断  vBitsPerPixels := cBitsPerPixels[mBitmapMain.PixelFormat];
      if vBitsPerPixels = 0 then Exit;
      vBytesSub := (mBitmapSub.Width * vBitsPerPixels + 7) div 8;
      vBytesMain := (mBitmapMain.Width * vBitsPerPixels + 7) div 8;
      if (vBytesSub = 0) or (vBytesMain = 0) then Exit;
      SetLength(vStrSub, vBytesSub);
      SetLength(vStrMain, vBytesMain);  vLine := mBitmapSub.ScanLine[0];
      Move(vLine^, vStrSub[1], vBytesSub);
      for I := 0 to mBitmapMain.Height - 1 do
      begin
        vLine := mBitmapMain.ScanLine[I];
        Move(vLine^, vStrMain[1], vBytesMain);
        J := Pos(vStrSub, vStrMain); //寻找子位图第一行是否存在主位图的一行中
        L := J;
        while J > 0 do
        begin
          vFlag := True;
          for K := 1 to mBitmapSub.Height - 1 do
          begin
            if I + K >= mBitmapMain.Height then //边界判断
            begin
              vFlag := False;
              Break;
            end;
            vLine := mBitmapMain.ScanLine[I + K];
            Move(vLine^, vStrMain[1], vBytesMain);
            vLine := mBitmapSub.ScanLine[K];
            Move(vLine^, vStrSub[1], vBytesSub);
            if not CompareMem(@vStrSub[1], @vStrMain[J], vBytesSub) then //判断子位图之后的行以相应主位图是否一致
            begin
              vLine := mBitmapMain.ScanLine[I];
              Move(vLine^, vStrMain[1], vBytesMain);
              vLine := mBitmapSub.ScanLine[0];
              Move(vLine^, vStrSub[1], vBytesSub);
              vFlag := False; //不一致打上标记
              Break;
            end;
          end;
          if vFlag then //一致则返回
          begin
            Result := Point((J - 1) div vBitsPerPixels * 8, I);
                            //计算多少像素位置
            Break;
          end;
          J := Pos(vStrSub, Copy(vStrMain, L + 1, MaxInt)); //考虑子位图第一行在主位图`后面还会出现的情况
          if J > 0 then
          begin
            J := L + J;
            L := J;
          end;
        end;
      end;
    end; { FindBitmapPoint }procedure TForm1.Button1Click(Sender: TObject);
    var
      vPoint: TPoint;
    begin
      vPoint := FindBitmapPoint(Image1.Picture.Bitmap, Image2.Picture.Bitmap);  ///////Begin 测试输出用
      Caption := Format('%d,%d', [vPoint.X, vPoint.Y]);
      if vPoint.X < 0 then Exit;
      Bevel1.Width := Image2.Picture.Bitmap.Width;
      Bevel1.Height := Image2.Picture.Bitmap.Height;
      Bevel1.Left := Image1.Left + vPoint.X;
      Bevel1.Top := Image1.Top + vPoint.Y;
      ///////End 测试输出用
    end;