MoveFileEx() returns ERROR_SHARING_VIOLATION

1.4k views Asked by At

I'm developing a program which could do live-update to modules of our main program.

If the main exe is running, it needs to

1) rename it to temporary name, eg: %productpath%\main.exe -> %productpath%\temp\temp.exe
::MoveFileEx(%productpath%\main.exe, %productpath%\temp\temp.exe, MOVEFILE_REPLACE_EXISTING) --- GetLastError() returns ERROR_SHARING_VIOLATION

2) delete temporary file until reboot
::MoveFileEx(%productpath%\temp\temp.exe, NULL, MOVEFILE_DELAY_UNTIL_REBOOT);

3) copy new downloaded exe to original path %productpath%\main.exe

My questions is why does it fail in the first step, where MoveFileEx() returns ERROR_SHARING_VIOLATION because the exe is running?

My update program has Administrator rights.

2

There are 2 answers

1
David Heffernan On

My questions is why does it fail in the first step, where MoveFileEx() returns ERROR_SHARING_VIOLATION because the exe is running?

Because when windows starts a process, it locks its executable to prevent modification. That way, windows doesn't need to load the entire image into memory, and can page it in on demand.

0
liu jia On

I've figured it out, anyway thanks a lot!

the error ERROR_SHARING_VIOLATION I've met when call MoveFileEx(), is because there's a HANDLE LEAK. Before update the exe/dll file, I've calculated the file MD5 to compare with the value got from Server side, but it missed a CloseHandle() call... so it means it's impossible to rename a running exe in another exe which open that running exe. When I add ClosedHandle(), it could work, the running exe can be renamed to another temp folder without any problem.