本帖最后由 tubaba 于 2014-9-9 09:54 编辑
#Region ;**** 参数创建于 ACNWrapper_GUI ****
#PRE_Res_requestedExecutionLevel=None
#EndRegion ;**** 参数创建于 ACNWrapper_GUI ****
#include-once
#include<array.au3>
#include <WinAPI.au3>
#include <File.au3>
Global $aArrayDirList[1][1], $aArrayint[1][1], $BackupFilePath, $ChangeFlag = False
_Initialization()
Global $endoffset = _ReadFileInfo($BackupFilePath)
;~ _Tablecreate($aArrayDirList,$Dir)
;~ _ArrayDisplay($aArrayDirList)
;~ _WriteTable($aArrayDirList)
;~ Local $res = _ReadIncludeini(_ReadHexData('\Config.ini'), 'Data', 'ExePath', '无')
;~ SourceFileRestore()
Func _Initialization()
Local $szDrive, $szDir, $szFName, $szExt
Local $atempPath = _PathSplit(@ScriptFullPath, $szDrive, $szDir, $szFName, $szExt)
$BackupFilePath = @TempDir & "\" & $atempPath[3] & $atempPath[4] & "-binbackup"
OnAutoItExitRegister("_OnAutoItExit")
If @Compiled Then
FileDelete($BackupFilePath)
FileCopy(@ScriptFullPath, $BackupFilePath, 1 + 8)
Else
MsgBox(0, "", "请编译后再运行")
EndIf
EndFunc ;==>_Initialization
Func _ReadFileInfo($BackupFilePath)
Local $val
Local $CurrentFileSize = FileGetSize($BackupFilePath)
$end = _HexRead($BackupFilePath, $CurrentFileSize - 4, 4)
If $end == "0xFFFF0008" Then
$tableOffset = Dec(Hex(_HexRead($BackupFilePath, $CurrentFileSize - 8, 4))) - 4
If _HexRead($BackupFilePath, $tableOffset + 4, 4) <> '0xFFFF0008' Then
$val = FileGetSize($BackupFilePath)
Return SetError(0, 1, $val)
Else
$val = $tableOffset
Return SetError(0, 2, $val)
EndIf
Else
$val = FileGetSize($BackupFilePath)
Return SetError(0, 1, $val)
EndIf
EndFunc ;==>_ReadFileInfo
Func _FileListToArrayEX(ByRef $aArray, $searchdir = @ScriptDir, $sFilter = '.*?', $iFlag = 0, $b_subdir = True, $s_ex = '')
Local $Dir = $searchdir
___FileList($aArray, $searchdir, $sFilter, $iFlag, $b_subdir, $s_ex, $Dir)
ReDim $aArray[$aArray[0][0] + 1][UBound($aArray, 2) + 1]
EndFunc ;==>_FileListToArrayEX
Func ___FileList(ByRef $aArray, $searchdir, $sFilter, $iFlag, $b_subdir, $s_ex, $Dir)
Local $iStep = 40000
If $aArray[0][0] = '' Then $aArray[0][0] = 0
Local $file
$search = FileFindFirstFile($searchdir & "\*.*")
If $search = -1 Then Return -1
While 1
$file = FileFindNextFile($search)
If @error Then
FileClose($search)
Return
ElseIf $file = "." Or $file = ".." Then
ContinueLoop
ElseIf StringInStr(FileGetAttrib($searchdir & "\" & $file), "D") Then
If ($iFlag = 2 Or $iFlag = 0) And StringRegExp($file, $sFilter, 0) = 1 Then
If $s_ex <> '' And StringRegExp($file, $s_ex, 0) Then ContinueLoop
If UBound($aArray, 1) <= $aArray[0][0] + 1 Then ReDim $aArray[UBound($aArray, 1) + $iStep][4]
$aArray[$aArray[0][0] + 1][0] = StringReplace($searchdir & "\" & $file, $Dir, '')
$aArray[$aArray[0][0] + 1][1] = $searchdir & "\" & $file
$aArray[$aArray[0][0] + 1][2] = 'D'
$aArray[0][0] += 1
EndIf
If $b_subdir Then ___FileList($aArray, $searchdir & "\" & $file, $sFilter, $iFlag, $b_subdir, $s_ex, $Dir)
ContinueLoop
EndIf
If StringRegExp($file, $sFilter, 0) = 1 And $iFlag <> 2 Then;正则匹配
If $s_ex <> '' And StringRegExp($file, $s_ex, 0) Then ContinueLoop
If UBound($aArray, 1) <= $aArray[0][0] + 1 Then ReDim $aArray[UBound($aArray, 1) + $iStep][4]
$aArray[$aArray[0][0] + 1][0] = StringReplace($searchdir & "\" & $file, $Dir, '')
$aArray[$aArray[0][0] + 1][1] = $searchdir & "\" & $file
$aArray[$aArray[0][0] + 1][2] = 'F'
$aArray[$aArray[0][0] + 1][3] = FileGetSize($searchdir & "\" & $file)
$aArray[0][0] += 1
EndIf
WEnd
EndFunc ;==>___FileList
Func _Tablecreate(ByRef $aArray, $Dir)
_FileListToArrayEX($aArray, $Dir)
Local $val = 4
For $i = 1 To UBound($aArray) - 1
If $aArray[$i][2] == 'F' Then
$val += $aArray[$i][3]
$aArray[$i][4] = $val
EndIf
Next
For $i = UBound($aArray) - 1 To 1 Step -1
If $aArray[$i][4] <> '' Then
$n = $i
Do
$n -= 1
If $n = 0 Then ExitLoop
Until $aArray[$n][4] <> ''
$aArray[$i][4] = $aArray[$n][4]
EndIf
Next
EndFunc ;==>_Tablecreate
Func _UnpackFile()
Local $tablestartoffset = $endoffset
Local $tablelen = Dec(Hex(_HexRead($BackupFilePath, $tablestartoffset + 8, 4)))
$tableendoffset = Dec(Hex(_HexRead($BackupFilePath, $tablestartoffset + 12, 4)))
Local $HexDataStartOffset = $tableendoffset + 4 + 1
Local $sBinString = _HexRead($BackupFilePath, $tablestartoffset + 16, $tablelen)
Local $sString = BinaryToString($sBinString)
Local $filetable = StringSplit($sString, '|')
Local $fileinfo, $filepath, $filetype, $filesize, $fileoffset
Local $exeunpackpath = @TempDir & '\exeunpack'
For $i = 1 To UBound($filetable) - 1
$fileinfo = StringSplit($filetable[$i], ':')
;~ $filepath = StringRegExpReplace($fileinfo[1], '(.*)\\', '')
$filepath = $exeunpackpath & $fileinfo[1]
$filetype = $fileinfo[2]
$filesize = $fileinfo[3]
$fileoffset = Number($fileinfo[4])
If $filetype == 'F' Then
Local $HexData = _HexRead($BackupFilePath, $HexDataStartOffset + $fileoffset, $filesize)
Local $hdle = FileOpen($filepath, 2 + 8 + 16)
FileWrite($hdle, $HexData)
FileClose($hdle)
;~ FileWrite('log.log', $filepath & ' ' & Hex(Dec($HexDataStartOffset) + $fileoffset) & @CRLF)
Else
EndIf
Next
EndFunc ;==>_UnpackFile
Func _ReadHexData($BackupFilePath, $path) ;~以/开头的相对路径
Local $HexData
Local $tablestartoffset = $endoffset
Local $tablelen = Dec(Hex(_HexRead($BackupFilePath, $tablestartoffset + 8, 4)))
$tableendoffset = Dec(Hex(_HexRead($BackupFilePath, $tablestartoffset + 12, 4)))
Local $HexDataStartOffset = $tableendoffset + 4 + 1
Local $sBinString = _HexRead($BackupFilePath, $tablestartoffset + 16, $tablelen)
Local $sString = BinaryToString($sBinString)
Local $filetable = StringSplit($sString, '|')
Local $fileinfo, $filepath, $filetype, $filesize, $fileoffset
For $i = 1 To UBound($filetable) - 1
$fileinfo = StringSplit($filetable[$i], ':')
$filepath = $fileinfo[1]
If $filepath <> $path Then ContinueLoop
$filetype = $fileinfo[2]
$filesize = $fileinfo[3]
$fileoffset = Number($fileinfo[4])
If $filetype == 'F' Then
$HexData = _HexRead($BackupFilePath, $HexDataStartOffset + $fileoffset, $filesize)
EndIf
Next
Return SetError(0, 0, $HexData)
EndFunc ;==>_ReadHexData
Func _ReadIncludeini($HexData, $section, $Key, $Default)
Local $str = BinaryToString($HexData)
Local $s_Sec = _IncludeIniReadSection_str($str, $Section, 0)
If @error = 1 Then Return SetError(1, 0, $default)
If @error = 2 Then Return SetError(3, 0, $default)
Local $_key = StringRegExpReplace($key, '^\h*|\h*$', '')
Local $aVal = StringRegExp(@LF & $s_Sec & @LF, '(?i)\n\h*\Q' & $_key & '\E\h*\=\h*(\V*?)\h*\v', 1)
If @error Then Return SetError(2, 0, $default)
Return $aVal[0]
EndFunc ;==>_ReadIncludeini
Func _WriteTable($aArray)
Local $sString, $sStringBinLen
For $i = 1 To UBound($aArray) - 1
$sString &= $aArray[$i][0] & ':' & $aArray[$i][2] & ':' & $aArray[$i][3] & ':' & $aArray[$i][4] & '|'
Next
$sString = StringTrimRight($sString, 1) ;第一个文件相对路径:文件(文件夹):文件大小|第二个文件相对路径:文件(文件夹):文件大小......
$sStringBinLen = BinaryLen(StringToBinary($sString))
Local $tablestartoffset = $endoffset
_HexWrite($BackupFilePath, $tablestartoffset, 0)
_HexWrite($BackupFilePath, $tablestartoffset + 4, 0x0800FFFF)
_HexWrite($BackupFilePath, $tablestartoffset + 8, "0x" & Hex(Number($sStringBinLen), 8))
_HexWrite($BackupFilePath, $tablestartoffset + 12, "0x" & Hex(Number($tablestartoffset + 16 + $sStringBinLen - 1), 8))
_HexWrite($BackupFilePath, $tablestartoffset + 16, StringToBinary($sString))
Local $HexDataStartOffset = $tablestartoffset + 16 + $sStringBinLen
_HexWrite($BackupFilePath, $HexDataStartOffset, 0)
$HexDataOffset = $HexDataStartOffset + 4
For $i = 1 To UBound($aArray) - 1
If $aArray[$i][2] == 'F' Then
_HexWrite($BackupFilePath, $HexDataOffset + $aArray[$i][4], "0x" & Hex(_HexRead($aArray[$i][1], 0, $aArray[$i][3])))
EndIf
Next
_HexWrite($BackupFilePath, FileGetSize($BackupFilePath), 0)
_HexWrite($BackupFilePath, FileGetSize($BackupFilePath), '0x' & Hex($tablestartoffset + 4, 8))
_HexWrite($BackupFilePath, FileGetSize($BackupFilePath), 0x0800FFFF)
$ChangeFlag = True
EndFunc ;==>_WriteTable
Func _HexWrite($tagBinFilePath, $Offset, $BinaryValue)
Local $Buffer, $ptr, $bLen, $fLen, $hFile, $Result, $Written
$bLen = BinaryLen($BinaryValue)
$Buffer = DllStructCreate("byte[" & $bLen & "]")
DllStructSetData($Buffer, 1, $BinaryValue)
If @error Then Return SetError(5, @error, 0)
$ptr = DllStructGetPtr($Buffer)
$hFile = _WinAPI_CreateFile($tagBinFilePath, 3, 4, 0)
If $hFile = 0 Then Return SetError(6, @error, 0)
$Result = _WinAPI_SetFilePointer($hFile, $Offset)
$err = @error
If $Result = 0xFFFFFFFF Then
_WinAPI_CloseHandle($hFile)
Return SetError(7, $err, 0)
EndIf
$Result = _WinAPI_WriteFile($hFile, $ptr, $bLen, $Written)
$err = @error
_WinAPI_CloseHandle($hFile)
If Not $Result Then Return SetError(8, $err, 0)
Return SetError(0, 0, $Result)
EndFunc ;==>_HexWrite
Func _HexRead($tagBinFilePath, $Offset, $Length)
Local $Buffer, $ptr, $fLen, $hFile, $Result, $Read, $err, $Pos
If Not FileExists($tagBinFilePath) Then Return SetError(1, @error, 0)
$fLen = FileGetSize($tagBinFilePath)
If $Offset > $fLen Then Return SetError(2, @error, 0)
If $fLen < $Offset + $Length Then Return SetError(3, @error, 0)
$Buffer = DllStructCreate("byte[" & $Length & "]")
$ptr = DllStructGetPtr($Buffer)
$hFile = _WinAPI_CreateFile($tagBinFilePath, 2, 2, 0)
If $hFile = 0 Then Return SetError(5, @error, 0)
$Pos = $Offset
$Result = _WinAPI_SetFilePointer($hFile, $Pos)
$err = @error
If $Result = 0xFFFFFFFF Then
_WinAPI_CloseHandle($hFile)
Return SetError(6, $err, 0)
EndIf
$Read = 0
$Result = _WinAPI_ReadFile($hFile, $ptr, $Length, $Read)
$err = @error
If Not $Result Then
_WinAPI_CloseHandle($hFile)
Return SetError(7, $err, 0)
EndIf
_WinAPI_CloseHandle($hFile)
If Not $Result Then Return SetError(8, @error, 0)
$Result = DllStructGetData($Buffer, 1)
Return SetError(0, 0, $Result)
EndFunc ;==>_HexRead
Func SourceFileRestore($BackupFilePath)
$CurrentFileSize = FileGetSize($BackupFilePath)
$end = _HexRead($BackupFilePath, FileGetSize($BackupFilePath) - 4, 4)
If $end <> "0xFFFF0008" Then Return SetError(1, 0, 1)
$tableOffset = Dec(Hex(_HexRead($BackupFilePath, FileGetSize($BackupFilePath) - 8, 4))) - 4
If _HexRead($BackupFilePath, $tableOffset + 4, 4) <> '0xFFFF0008' Then Return SetError(2, 0, 2)
$HexData = _HexRead($BackupFilePath, 0, $tableOffset)
Local $hdle = FileOpen($BackupFilePath, 2 + 8 + 16)
FileWrite($hdle, $HexData)
FileClose($hdle)
Return SetError(0,0,0)
EndFunc ;==>SourceFileRestore
Func _IncludeIniReadSection_str($Data, $Section, $mode = 0, $nFlag = 0)
Local $_Section = StringRegExpReplace($Section, '^\h*|\h*$', '')
Local $s_Sec = StringRegExp($Data, '(?si)(?:^|\n)\h*\[\h*\Q' & $_Section & '\E\h*\](.+?)(?=\r?\n\h*\[|$)', 3)
If @error Then Return SetError(1, 0, 0)
$line_all = $s_Sec[0]
If $nFlag Then
For $i = 1 To UBound($s_Sec) - 1
$line_all &= $s_Sec[$i]
Next
EndIf
If Not StringRegExp($line_all, '\V') Then Return SetError(2, 0, 0)
Return $line_all
EndFunc ;==>_IncludeIniReadSection_str
Func _OnAutoItExit()
If @Compiled And $ChangeFlag Then
_Selfcopy(2)
Else
FileDelete($BackupFilePath)
EndIf
If IsDeclared('Unpack') Then DirRemove(Eval('Unpack'), 1)
If IsDeclared('fShe') Then FileDelete(Eval('fShe'))
Exit
EndFunc ;==>_OnAutoItExit
;~ Func _Selfcopy($iDelay = 0)
;~ Local $sCmdFile
;~ $sCmdFile = 'ping -n ' & $iDelay & ' 127.0.0.1 > nul &' & _
;~ 'copy /y "' & $BackupFilePath & '" "' & @ScriptFullPath & '" > nul&' & _
;~ 'del "' & $BackupFilePath & '" > nul&call "' & @ScriptFullPath & '"'
;~ Run(@ComSpec & ' /c ' & $sCmdFile, @ScriptDir, @SW_HIDE)
;~ EndFunc ;==>_Selfcopy
Func _Selfcopy($iDelay = 0)
Local $szDrive, $szDir, $szFName, $szExt
Local $atempPath = _PathSplit(@ScriptFullPath, $szDrive, $szDir, $szFName, $szExt)
Local $sCmdFile
Local $file = FileOpen(@TempDir & "\scratch.bat", 2 + 8)
$sCmdFile = ':loop1' & @CRLF _
& 'ping -n ' & $iDelay & ' 127.0.0.1 > nul' & @CRLF _
& 'del /q "' & @ScriptFullPath & '"' & @CRLF _
& 'set /a num+=1' & @CRLF _
& 'if %num% gtr 10 (goto loop2)' & @CRLF _
& 'if exist "' & @ScriptFullPath & '" goto loop1' & @CRLF _
& 'goto loop3' & @CRLF _
& ':loop2' & @CRLF _
& 'set num=0' & @CRLF _
& 'taskkill /f /im "' & $atempPath[3] & $atempPath[4] & '"' & @CRLF _
& 'ping -n ' & $iDelay & ' 127.0.0.1 > nul' & @CRLF _
& 'if exist "' & @ScriptFullPath & '" goto loop1' & @CRLF _
& ':loop3' & @CRLF _
& 'copy /y "' & $BackupFilePath & '" "' & @ScriptFullPath & '"' & @CRLF _
& 'ping -n ' & $iDelay & ' 127.0.0.1 > nul' & @CRLF _
& 'if not exist "' & @ScriptFullPath & '" goto loop3' & @CRLF _
& 'del /q "' & $BackupFilePath & '"' & @CRLF _
& 'start "" "' & @ScriptFullPath & '"' & @CRLF _
& ':loop4' & @CRLF _
& 'del /q %0' & @CRLF _
& 'ping -n ' & $iDelay & ' 127.0.0.1 > nul' & @CRLF _
& 'if exist "' & @TempDir & '\scratch.bat" goto loop4' & @CRLF _
& 'exit'
FileWrite($file, $sCmdFile)
FileClose($file)
ShellExecute(@TempDir & "\scratch.bat", '', @SystemDir, 'open', @SW_HIDE)
Exit
EndFunc ;==>_Selfcopy |