Fortran Coder

标题: 隐藏文件到exe中 [打印本页]

作者: andy8496    时间: 2023-2-1 15:23
标题: 隐藏文件到exe中
有没有办法把一个文件(图片,office文档等),隐藏到Fortran的exe中,运行这个exe的时候自动释放出来,运行结束了再删掉?

作者: fcode    时间: 2023-2-1 16:52
windows系统的话,可以包含在 Resource 资源里。
然后通过 FindResourceEx,LoadResource,SizeofResource 这几个函数,得到资源体。Open , Write 到文件里去。
[Fortran] 纯文本查看 复制代码
  Logical Function WriteResourceToFile( resType , resID , fileName ) result(ok)
    use , intrinsic :: ISO_C_Binding
    use kernel32 , only : SizeofResource , LockResource , LoadResource , FindResourceEx
    Character(Len=*) , intent(IN) :: resType , fileName
    Integer , intent(IN) :: resID
    character(len=len_trim(resType)+1) :: myType
    character , pointer :: pMem(:)
    integer :: hRes,hMem, j
    type(c_ptr) :: cp
    ok = .false.
    myType = trim(resType)//c_null_char
    hRes = FindResourceEx(0,transfer(c_loc(myType),j),resID,0_2)
    if( hRes == 0 ) return
    hMem = LoadResource(0,hRes)
    if( hMem == 0 ) return
    hMem = LockResource( hMem )
    if( hMem == 0 ) return
    j = SizeofResource(0,hRes)
    if( j == 0 ) return
    call c_f_pointer( transfer( hMem , cp ) , pMem , [j] )
    Open(NewUnit = j , File = fileName , access="stream")
    write(j) pMem
    Close(j)
    ok = .true.
  End Function WriteResourceToFile




作者: andy8496    时间: 2023-2-1 17:51
fcode 发表于 2023-2-1 16:52
windows系统的话,可以包含在 Resource 资源里。
然后通过 FindResourceEx,LoadResource,SizeofResource  ...

多谢回复!
这些是Windows的API?大致理解原理了,但是在Fortran中怎么用这些函数?能否帮忙做个Demo?
作者: fcode    时间: 2023-2-1 19:11
你用的什么编译器?
作者: andy8496    时间: 2023-2-1 19:32
本帖最后由 andy8496 于 2023-2-1 19:34 编辑
fcode 发表于 2023-2-1 16:52
windows系统的话,可以包含在 Resource 资源里。
然后通过 FindResourceEx,LoadResource,SizeofResource  ...

非常感谢!
恕我愚钝, 没懂函数的参数什么意思
Function WriteResourceToFile( resType , resID , fileName )
resType : 如果是二进制文件,应该如何指定该类型?直接用资源文件后缀名可否?
resID : 如何得到这个ID?我查了函数原型:

HRSRC FindResourceEx(HXODULE hModule,LPCTSTR lpType,LPCTSTR lpName,WORD wLanguage);

参数:

lpName:指向说明资源文件名称并以NULL为结束符的字符串。若要了解更多的信息,请参见注意部分。
这是不是应该是资源文件的名称字符串?
如果确为整数ID,我调用此函数前应该如何得到该ID?
另外,0_2,是什么意思呢?

作者: andy8496    时间: 2023-2-1 19:34
本帖最后由 andy8496 于 2023-2-1 19:40 编辑
fcode 发表于 2023-2-1 19:11
你用的什么编译器?

VS+IVF+Win7
奇怪,好像我在Resource Files里面加不加文件,编译出来的exe大小是一样的。

作者: fcode    时间: 2023-2-1 20:36
andy8496 发表于 2023-2-1 19:34
VS+IVF+Win7
奇怪,好像我在Resource Files里面加不加文件,编译出来的exe大小是一样的。
...

先添加资源文件 *.rc
然后在 rc文件里导入被包含文件
作者: fcode    时间: 2023-2-1 20:41
andy8496 发表于 2023-2-1 19:32
非常感谢!
恕我愚钝, 没懂函数的参数什么意思
Function WriteResourceToFile( resType , resID , fileNa ...

windows 的资源有不同的类型,例如字符串表,位图,菜单,对话框,图标,版权信息。
这些都是windows资源内置的类型。你也可以自定义类型,比如类型名为 ABC。
lpType 指向类型名。

每个类型可以有多个文件。例如可以有2个菜单,3个对话框等等。每一个有自己独有的名称。
lpName 指向名称。
名称也可以是整型(需要小于65535),就是一个编号。(我的例子中的 resID)

每个文件又可以有不同的语言版本,这样可以实现在英文系统就是英文的资源,中文系统就是中文的资源(例如菜单等)
0_2 表示 kind=2 的整数 0,在例子中充当 WORD wLanguage 语言。
作者: andy8496    时间: 2023-2-1 22:39
andy8496 发表于 2023-2-1 19:32
非常感谢!
恕我愚钝, 没懂函数的参数什么意思
Function WriteResourceToFile( resType , resID , fileNa ...

终于成功了!如果我想编译成64位的,
use kernel32 , only : SizeofResource , LockResource , LoadResource , FindResourceEx
需要改成什么名字?
作者: fcode    时间: 2023-2-2 08:35
andy8496 发表于 2023-2-1 22:39
终于成功了!如果我想编译成64位的,
use kernel32 , only : SizeofResource , LockResource , LoadResou ...

好的,我改得严谨一点,可以兼容x86和x64。
另外,你可以尝试在 rc 文件里包含一个 ico 图标,和版权信息。不用写任何代码,就有效果。很有趣。

[Fortran] 纯文本查看 复制代码
Logical Function WriteResourceToFile( resType , resID , fileName ) result(ok)
  use , intrinsic :: ISO_C_Binding
  use kernel32 , only : WORD,LPVOID,HANDLE, &
    SizeofResource , LockResource , LoadResource , FindResourceEx
  Character(Len=*) , intent(IN) :: resType , fileName
  Integer(LPVOID) , intent(IN) :: resID
  integer(HANDLE) :: hRes,hMem
  integer :: j
  character(len=len_trim(resType)+1) :: myType
  character , pointer :: pMem(:)
  type(c_ptr) :: cp
  ok = .false.
  myType = trim(resType)//c_null_char
  hRes = FindResourceEx(0_HANDLE,transfer(c_loc(myType),hRes),resID,0_WORD)
  if( hRes == 0_HANDLE ) return
  hMem = LoadResource(0_HANDLE,hRes)
  if( hMem == 0_HANDLE ) return
  hMem = LockResource( hMem )
  if( hMem == 0_HANDLE ) return
  j = SizeofResource(0_HANDLE,hRes)
  if( j == 0 ) return
  call c_f_pointer( transfer( hMem , cp ) , pMem , [j] )
  Open(NewUnit = j , File = fileName , access="stream")
  write(j) pMem
  Close(j)
  ok = .true.
End Function WriteResourceToFile


作者: andy8496    时间: 2023-2-2 10:33
fcode 发表于 2023-2-2 08:35
好的,我改得严谨一点,可以兼容x86和x64。
另外,你可以尝试在 rc 文件里包含一个 ico 图标,和版权信息 ...

多谢多谢!昨天试了下版权信息。资源以前没用过,有点打开新世界的感觉。
作者: fcode    时间: 2023-2-2 10:57
andy8496 发表于 2023-2-2 10:33
多谢多谢!昨天试了下版权信息。资源以前没用过,有点打开新世界的感觉。 ...

这是个windows的小把戏。不用太用精力关注它。




欢迎光临 Fortran Coder (http://bbs.fcode.cn/) Powered by Discuz! X3.2