VB.NET 复制自己然后 运行 复制失败

VB.NET Copying myself and then run the copy fails

我正在尝试 运行 我的项目,将其自身复制到 update.exe 然后 运行 update.exe 以测试更新常规。

我遇到的问题是 exe 文件已成功复制,但是当 update.exe 启动时,它总是崩溃。

如果我从崩溃中中止 update.exe 程序,但我的主 exe 仍然是 运行,我可以从资源管理器中启动 update.exe 并且一切正常。如果从另一个 exe 文件复制后启动它,我终生无法弄清楚为什么 update.exe 会崩溃。

代码如下:

Public Class Updater
    Public sFullname As String
    Public sExename As String
    Public sArguments As String

    Public Sub New()
        'Constructor

        Me.Initiate()
        Me.FakeUpdate()
        Me.DoUpdate()

        'MsgBox(Me.sFullname)

    End Sub

    Private Sub Initiate()
        Dim sCmdLine As String = Environment.CommandLine()
        Dim iPos = sCmdLine.IndexOf("""", 2)
        Me.sFullname = sCmdLine.Substring(1, iPos - 1).Trim()
        Dim iPos2 = sFullname.LastIndexOf("\")
        Me.sExename = sFullname.Substring(iPos2 + 1).Trim()
        Me.sArguments = sCmdLine.Substring(iPos + 1).Trim()

    End Sub

    Private Sub FakeUpdate()
        'If we start the app with -fakeupdate parameter, copy myself to update.exe, then run update.exe to debug the update process.
        If Me.sArguments = "-fakeupdate" Then
            FileCopy(Me.sFullname, "update.exe")
            Shell("update.exe")
        End If
    End Sub

    Private Sub DoUpdate()
        If Me.sExename = "update.exe" Then
            MsgBox("DoUpdate called from update.exe")
        End If
    End Sub
End Class

Public Class Form1
    Private Sub Form1_Load(ByVal sender As Object, ByVal e As System.EventArgs) Handles Me.Load
        Dim Updater As New Updater
    End Sub
End Class

项目配置为 运行s 带有参数 -fakeupdate

该代码是一个更大项目的一部分,但我已注释掉所有其他代码,但仍然收到此错误。

我从 update.exe 得到的错误:长度不能小于 null。参数名称:长度

System.ArgumentOutOfRangeException: Length cannot be less than null.
Parameternaam: length
   bij System.String.InternalSubStringWithChecks(Int32 startIndex, Int32 length, Boolean fAlwaysCopy)
   bij Todo_List.Updater.Initiate() in S:\VB Projects\Todo List\Todo List\Form1.vb:regel 19
   bij Todo_List.Updater..ctor() in S:\VB Projects\Todo List\Todo List\Form1.vb:regel 8
   bij Todo_List.Form1.Form1_Load(Object sender, EventArgs e) in S:\VB Projects\Todo List\Todo List\Form1.vb:regel 594
   bij System.EventHandler.Invoke(Object sender, EventArgs e)
   bij System.Windows.Forms.Form.OnLoad(EventArgs e)
   bij System.Windows.Forms.Control.CreateControl(Boolean fIgnoreVisible)
   bij System.Windows.Forms.Control.CreateControl()
   bij System.Windows.Forms.Control.WmShowWindow(Message& m)
   bij System.Windows.Forms.Control.WndProc(Message& m)
   bij System.Windows.Forms.Control.ControlNativeWindow.WndProc(Message& m)
   bij System.Windows.Forms.NativeWindow.Callback(IntPtr hWnd, Int32 msg, IntPtr wparam, IntPtr lparam)

编辑:小更新,如果我什至不复制文件也会出错。只是 shell("update.exe") 出错了。我什至在表单上创建了一个按钮以在单击时启动它,但每次都失败。但是如果我 运行 它来自资源管理器,一切都很好。

这是一个奇怪的行为,甚至可能是一个错误,但我想通了。

显然,如果您使用 shell ("program.exe") 启动一个程序,并从该程序中调用 Environment.CommandLine(),它将只是 program.exe,而如果您双击该程序explorer 它将改为 C:\MyPath\program.exe。

为了解决这个问题,我不得不按如下方式更改我的代码:

    Private Sub FakeUpdate()
        Dim sShell As String
        'If we start the app with -fakeupdate parameter, copy myself to update.exe, then run update.exe to debug the update process.
        If Me.sArguments = "-fakeupdate" Then
            FileCopy(Me.sFullname, "update.exe")

            sShell = My.Computer.FileSystem.CurrentDirectory & "\update.exe"

            Shell(sShell)
        End If
    End Sub

现在它可以正常工作,无论是从资源管理器还是从程序内部启动程序。