Вот код. Вопросы:
1. Почему в конце возникает "Access Violation..."
2. Почему, если я ставлю BlockSize = больше чем 2К (например я хочу читать блоками по 64К = 65536, например для больших файлов), то ReadFile возвращает 'Fuck again'.
3. И если все успешно, то в BP оказываются считанные данные. У меня не получается загнать это в строку.
Подскажите уважаемые гуру что я делаю не так
procedure TForm1.Button1Click(Sender: TObject);
var
fSrc: string;
StartByte: integer;
BP : array of byte;
hFile, cRet, BytesWorked, BlockSize: Cardinal;
srcFileSize: DWORD;
bRet: Boolean;
begin
fSrc := 'C:\autoexec.bat';
hFile := CreateFile(PChar(fSrc), GENERIC_READ, 0, nil, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, 0);
srcFileSize := GetFileSize(hFile, nil);
//ShowMessage('File size = ' + IntToStr(srcFileSize) + ' Err = ' + IntToStr(GetLastError));
StartByte := 0;
BlockSize := 1024;
cRet := SetFilePointer(hFile, StartByte, nil, FILE_BEGIN);
SetLength(BP, Sizeof(byte) * BlockSize);
bRet := ReadFile(hFile, BP, BlockSize, BytesWorked, nil);
if BytesWorked > 0 then
ShowMessage('OK')
else
ShowMessage('Fuck again! :(');
CloseHandle(hFile);
end;
Не вполне уверен, что Вас это спасет, но если обявить массив как
var BP: array[0..XXX] of Byte;
(т.е. размер массива фиксирован) и убрать SetLength, то все три Ваши проблемы решаются. Можно даже как
var BP: array[0..XXX] of Char;
Тогда и в строку проще преобразовывать...
Здравствуйте, balykovdron, Вы писали:
B>Вот код. Вопросы:
B>1. Почему в конце возникает "Access Violation..."
B>2. Почему, если я ставлю BlockSize = больше чем 2К (например я хочу читать блоками по 64К = 65536, например для больших файлов), то ReadFile возвращает 'Fuck again'.
B>3. И если все успешно, то в BP оказываются считанные данные. У меня не получается загнать это в строку.
B>Подскажите уважаемые гуру что я делаю не так
B>B>procedure TForm1.Button1Click(Sender: TObject);
B>var
B> fSrc: string;
B> StartByte: integer;
B> BP : array of byte;
B> hFile, cRet, BytesWorked, BlockSize: Cardinal;
B> srcFileSize: DWORD;
B> bRet: Boolean;
B>begin
B> fSrc := 'C:\autoexec.bat';
B> hFile := CreateFile(PChar(fSrc), GENERIC_READ, 0, nil, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, 0);
B> srcFileSize := GetFileSize(hFile, nil);
B> //ShowMessage('File size = ' + IntToStr(srcFileSize) + ' Err = ' + IntToStr(GetLastError));
B> StartByte := 0;
B> BlockSize := 1024;
B> cRet := SetFilePointer(hFile, StartByte, nil, FILE_BEGIN);
B> SetLength(BP, Sizeof(byte) * BlockSize);
B> bRet := ReadFile(hFile, BP, BlockSize, BytesWorked, nil);
B> if BytesWorked > 0 then
B> ShowMessage('OK')
B> else
B> ShowMessage('Fuck again! :(');
B> CloseHandle(hFile);
B>end;
B>
Здравствуйте, balykovdron, Вы писали:
B>Вот код. Вопросы:
B>1. Почему в конце возникает "Access Violation..."
потому что надо вместо
bRet := ReadFile(hFile, BP, BlockSize, BytesWorked, nil);
писать
bRet := ReadFile(hFile, BP[0], BlockSize, BytesWorked, nil);
B>2. Почему, если я ставлю BlockSize = больше чем 2К (например я хочу читать блоками по 64К = 65536, например для больших файлов), то ReadFile возвращает 'Fuck again'.
По той же причине. Только чтобы это выяснить надо не ругаться, а написать
var lpMsgBuf : array[0..1024] of char{PChar};
FormatMessage(
FORMAT_MESSAGE_FROM_SYSTEM,
nil,
GetLastError(),
LANG_NEUTRAL,
lpMsgBuf,
1024{0},
nil
);
ShowMessage(string(lpMsgBuf));
И получишь более информативное сообщение Invalid access to memory location
B>3. И если все успешно, то в BP оказываются считанные данные. У меня не получается загнать это в строку.
str := string(BP);
J>J>bRet := ReadFile(hFile, BP[0], BlockSize, BytesWorked, nil);
J>
Да верно. Еще вот так у меня получилось.
bRet := ReadFile(hFile, BP^, BlockSize, BytesWorked, nil);
B>2. Почему, если я ставлю BlockSize = больше чем 2К (например я хочу читать блоками по J>По той же причине. Только чтобы это выяснить надо не ругаться, а написать
J>J>var lpMsgBuf : array[0..1024] of char{PChar};
J> FormatMessage(
J> FORMAT_MESSAGE_FROM_SYSTEM,
J> nil,
J> GetLastError(),
J> LANG_NEUTRAL,
J> lpMsgBuf,
J> 1024{0},
J> nil
J> );
J> ShowMessage(string(lpMsgBuf));
J>
За этот кусок болошое спасибо. У меня на VB такой кусок был все лень было переписать на D.
B>3. И если все успешно, то в BP оказываются считанные данные. У меня не получается загнать это в строку.
J>J> str := string(BP);
J>
Спасибо! Все пучком!