![]() |
| ||
|
|
Новости |
Поиск |
FAQ |
Статьи |
Книги |
Новости VCL
| | Форумы ЧАТ |
Орешник |
|
| |||
| |||
« предыдущая ветвь | форум | следующая ветвь »
Работа со строками приводит к ошибкам при выделении памяти [D5, D7, Win95/98]
MegaVolt © (2006-12-28 16:34:00)Многократный вызов нижеприведёённого кода приводит к проблемам с выделением памяти и нестабильной работе программы. Может ли быть такое и как можно решить эту проблему.
LogFile:TFileStream;
procedure TLog.StartF(Str: string);
var
s:string;
begin
if not Enabled then Exit;
s:='<'+IntToStr(GetTickCount-StartTime)+':'+str+#13+#10;
LogFile.Write(s[1],Length(s));
// FlushFileBuffers(LogFile.Handle);
end;
Допускаю что дело не в этой функции а во вносимых ею задержках. Но как тогда искать в чём проблема?
MegaVolt (2006-12-29 16:21:00) [1]>я ему на пальцах нарисовал что даже 1 байт не может быть потокобезопасным
А можно ссылочку? Или повторить вывод? (я надеюсь нерассматривался случай побитового исправления байта?)
Sha (2006-12-29 13:21:00) [2]> AgainSlymRO (29.12.06 13:02) [26]
> Сабрались старые бухарики под новый год и спорять по IsMultiThread...
> CriticalSection на разделяемом несколькими потоками объекте должен быть априори, всегда!
Ну да, конечно, на CriticalSection свет клином сошелся
evvcom (2006-12-29 13:09:00) [3]> [26] AgainSlymRO (29.12.06 13:02)
> Сабрались старые бухарики под новый год
Гы, а ты вечный нарушитель? :)))
AgainSlymRO (2006-12-29 13:04:00) [4]Я тут с одним уже спорил, так этот "один" втирал мне что строки string потокобезопасны! я ему на пальцах нарисовал что даже 1 байт не может быть потокобезопасным
AgainSlymRO (2006-12-29 13:02:00) [5]Сабрались старые бухарики под новый год и спорять по IsMultiThread...
CriticalSection на разделяемом несколькими потоками объекте должен быть априори, всегда!
evvcom (2006-12-29 12:47:00) [6]> [23] Sha © (29.12.06 12:43)
> IsMultiThread=TRUE
А... Уже забыл, что раньше об этом говорилось.
Sha (2006-12-29 12:44:00) [7]> evvcom © (29.12.06 12:42) [22]
> Что-то я вас не пойму. Вы хотите сказать, что дельфовый менеджер памяти не потокобезопасен?
Потокобезопасен, если потоки создавать средствами Делфи.
Sha (2006-12-29 12:43:00) [8]> MegaVolt © (29.12.06 12:22) [20]
> Как тогда правильно делать ведение логов?
Если поток всего один, то ничего дополнительно делать не надо.
Если 2 и больше - установить IsMultiThread=TRUE, например при помощи BeginThread
Если пишущих в лог 2 и больше - защитить процедуру записи крит секцией.
evvcom (2006-12-29 12:42:00) [9]Что-то я вас не пойму. Вы хотите сказать, что дельфовый менеджер памяти не потокобезопасен?
Sha (2006-12-29 12:31:00) [10]> Джо © (29.12.06 12:22) [19]
> В метод StartF нельзя будет «войти» из разных потоков
Согласен.
> Поэтому и не будет никаких «параллельных обращений к менеджеру памяти».
Не согласен.
Другой поток имеет полное право в это время создать какой-нить объект.
MegaVolt (2006-12-29 12:22:00) [11]>Проблема может быть, например, в таком безобидном операторе
А похоже так и есть. Как тогда правильно делать ведение логов?
Джо (2006-12-29 12:22:00) [12]> [16] Sha © (29.12.06 12:06)
> > Джо © (29.12.06 11:05) [15]
> > А критические секции этому воспрепятствуют.
>
> Нет. Они нисколько не препятствуют параллельным обращениям
> к менеджеру памяти.
В методStartFнельзя будет «войти» из разных потоков. Поэтому и не будет никаких «параллельных обращений к менеджеру памяти». Разве не так?
Sha (2006-12-29 12:17:00) [13]> MegaVolt © (29.12.06 12:07) [17]
Проблема может быть, например, в таком безобидном операторе:
s:='<'+IntToStr(GetTickCount-StartTime)+':'+str+#13+#10;
т.к. он требует перераспределения памяти, если параллельному потоку в
тоже самое время потребуются услуги менеджера.
MegaVolt (2006-12-29 12:07:00) [14]Т.е. проблема в множественном обращении к FileStream?
Sha (2006-12-29 12:06:00) [15]> Джо © (29.12.06 11:05) [15]
> А критические секции этому воспрепятствуют.
Нет. Они нисколько не препятствуют параллельным обращениям к менеджеру памяти.
Джо (2006-12-29 11:05:00) [16]> Я не вижу ничего криминального в том что этот кусок кода
> будет выполнятся одновременно из нескольких мест.
Дык, как сказали, мультимедийный таймер выполняется в разных потоках. Поэтому и будут неприятности из-за паралельных обращений к глобальным переменным из разных потоков. А критические секции этому воспрепятствуют.
MegaVolt (2006-12-29 10:55:00) [17]Насколько я понимаю критические секции нужны чтобы данный кусок кода мог выполнялся только один раз и повторное обращение до окончания выполнения было бы невозможно. Почему это может помочь? Я не вижу ничего криминального в том что этот кусок кода будет выполнятся одновременно из нескольких мест.
Sha (2006-12-29 10:14:00) [18]> SlymRO (29.12.06 04:33) [11]
Припарки вряд ли помогут менеджеру.
Slym (2006-12-29 04:39:00) [19]Вау! Новогодняя амнистия!
SlymRO (2006-12-29 04:33:00) [20]
procedure TLog.StartF(Str: string);
var
s:string;
begin
if not Enabled then Exit;
CriticalSection.Enter;
try
s:='<'+IntToStr(GetTickCount-StartTime)+':'+str+#13+#10;
LogFile.Write(s[1],Length(s));
// FlushFileBuffers(LogFile.Handle);
finally
CriticalSection.Leave;
end;
end;