CopyFileEx в Windows 7 - PullRequest
       6

CopyFileEx в Windows 7

2 голосов
/ 08 октября 2010

Я пытаюсь использовать функцию CopyFileEx из kernel32.dll в Windows 7, используя взаимодействие .NET. MSDN говорит: Если lpProgressRoutine возвращает PROGRESS_STOP из-за того, что пользователь остановил операцию, CopyFileEx вернет ноль и GetLastError вернет ERROR_REQUEST_ABORTED. В этом случае частично скопированный файл назначения остается без изменений. В Windows XP код работает нормально, но в Windows 7 частичный файл удаляется автоматически. Я что-то пропустил?

using System;
using System.Runtime.InteropServices;

namespace Copy
{
    class Program
    {
        static void Main(string[] args)
        {
            var result = ExtendedCopy.XCopy("c:/original.rar", "c:/copy.rar");
        }
    }

    class ExtendedCopy
    {
        [DllImport("kernel32.dll", SetLastError = true, CharSet = CharSet.Unicode)]
        private static extern bool CopyFileEx(string lpExistingFileName, string lpNewFileName, CopyProgressRoutine lpProgressRoutine, IntPtr lpData, ref Int32 pbCancel, CopyFileFlags dwCopyFlags);

        delegate CopyProgressResult CopyProgressRoutine(long TotalFileSize, long TotalBytesTransferred, long StreamSize, long StreamBytesTransferred, uint dwStreamNumber, CopyProgressCallbackReason dwCallbackReason, IntPtr hSourceFile, IntPtr hDestinationFile, IntPtr lpData);

        enum CopyProgressResult : uint
        {
            PROGRESS_CONTINUE = 0,
            PROGRESS_CANCEL = 1,
            PROGRESS_STOP = 2,
            PROGRESS_QUIET = 3
        }

        enum CopyProgressCallbackReason : uint
        {
            CALLBACK_CHUNK_FINISHED = 0x0,
            CALLBACK_STREAM_SWITCH = 0x1
        }

        [Flags]
        enum CopyFileFlags : uint
        {
            COPY_FILE_FAIL_IF_EXISTS = 0x1,
            COPY_FILE_RESTARTABLE = 0x2,
            COPY_FILE_OPEN_SOURCE_FOR_WRITE = 0x4,
            COPY_FILE_ALLOW_DECRYPTED_DESTINATION = 0x8
        }

        public static bool XCopy(String oldFile, String newFile)
        {
            int pbCancel = 0;
            return CopyFileEx(oldFile, newFile, new CopyProgressRoutine(CopyProgressHandler), IntPtr.Zero, ref pbCancel, CopyFileFlags.COPY_FILE_RESTARTABLE);
        }

        private static CopyProgressResult CopyProgressHandler(long total, long transferred, long streamSize, long StreamByteTrans, uint dwStreamNumber, CopyProgressCallbackReason reason, IntPtr hSourceFile, IntPtr hDestinationFile, IntPtr lpData)
        {
            if (transferred > 10000000)
            {
                return CopyProgressResult.PROGRESS_STOP;
            }
            return CopyProgressResult.PROGRESS_CONTINUE;
        }
    }
}
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...