Перейти к содержанию
Fire Monkey от А до Я
  • 0

Убить поток TThread кроссплатформено


Akad

Вопрос

Есть TThread, который что-то там своё делает. При этом он может "подвиснуть", особенно на 3g TCP соединениях. И соответственно часто случается, что его надо "пристрелить" не дожидаясь пока он сам сообразит что пора закругляться. Под винду есть чудесная TerminateThread. Но как ту же задачу выполнить под Android? iOS?
 

Ссылка на комментарий

Рекомендуемые сообщения

  • 0

Если я не прав поправят, но я делаю так

uses Threading;

var

GetCodeTask: ITask;

      GetCodeTask := TTask.Create(
          procedure
         begin

              ...

         end);
 

  if GetCodeTask <> nil then
    if GetCodeTask.Status = TTaskStatus.Running then
      GetCodeTask.Cancel;

Ссылка на комментарий
  • 0

повис, да и пусть висит себе.

все равно прервать системную функцию вам не удастся раньше её функции желания

зато вы легко можете игнорировать результат выполнения такого потока, если/когда он все же вернется

 

Ссылка на комментарий
  • 0
4 часа назад, Камышев Александр сказал:

разорвать TCP сессию,

А как? Ну, на винде в теории можно из другого потока закрыть хендл соединения (если используемый для сетевого обмена компонент дает возможность получить хендл).

А вот кроссплатформенный штатный HTTPClient -???

Ссылка на комментарий
  • 0
1 час назад, kami сказал:

А как? Ну, на винде в теории можно из другого потока закрыть хендл соединения (если используемый для сетевого обмена компонент дает возможность получить хендл).

А вот кроссплатформенный штатный HTTPClient -???

Сдаюсь, кто их знает чего там в исходниках.

На винде хэндл закрыть, на unix pthread_cancel выводит из операции ввода-вывода или sleep в pthread.

TIdHTTP или TNetHTTPclient?

IdHTTP1->Socket->Close() - не поможет?

Изменено пользователем Камышев Александр
Ссылка на комментарий
  • 0
В 27 ноября 2017 г. в 15:53, FREEFAR сказал:

GetCodeTask: ITask;

Нужен полноценный поток, как отдельный класс.

Тем более

В 27 ноября 2017 г. в 15:53, FREEFAR сказал:

  if GetCodeTask <> nil then
    if GetCodeTask.Status = TTaskStatus.Running then
      GetCodeTask.Cancel;

Это явный краш всей системы. Когда поток высвободит ресурсы между if и cancel.

В 27 ноября 2017 г. в 16:05, krapotkin сказал:

повис, да и пусть висит себе.

Ага. Только когда он отвиснет, не будет ни сам существовать ни все переменные, которые в нём. А равно как и форма, один из компонентов которой он заполнял.

В 27 ноября 2017 г. в 16:05, krapotkin сказал:

зато вы легко можете игнорировать результат выполнения такого потока, если/когда он все же вернется

Под андроидом сложно игнорировать краш всей программы и закрытие её. По крайней мере у меня не получается. Если в одном из потоков тотальный краш - это всё.
 

Ссылка на комментарий
  • 0
3 минуты назад, Akad сказал:

Нужен полноценный поток, как отдельный класс.

А чем TTask не полноценен?

 

4 минуты назад, Akad сказал:

Это явный краш всей системы. Когда поток высвободит ресурсы между if и cancel.

Есть пример подтверждающий это утверждение? Просто у меня пока пол года  все работает.

Ссылка на комментарий
  • 0

а почему поток должен крешить систему, я не пойму?
не нужно из потока обращаться к переменным. можно задать ему обработчик OnTerminate
конечно и форма, из которой его вызвали может перестать существовать, но тогда просто обработчик вешать на то что существовать точно БУДЕТ

Ссылка на комментарий
  • 0
1 час назад, FREEFAR сказал:

А чем TTask не полноценен?

Как миниум нет полноценного класса. Но вопрос не в этом. Cancel не работает. Поток не убивает. Только что проверил на запросе который длится 6-7 сек. Через секунду потоку делаю Cancel, но он всё равно доходит до конца и даже память освобождает. В общем не работает.

1 час назад, FREEFAR сказал:

Есть пример подтверждающий это утверждение? Просто у меня пока пол года  все работает.

Оно очевидно из кода. :D

Любое межпоточное взаимодействие нужно осуществлять на локах (если нужно быстро, но в дельфе нет, только через апи). Ну или по извращённому/тормозному/но дельфёвому. Через Synchronize например. Ну если не интересно отлаживать приложение на устройствах клиента с разницей во времени часов в 12, и явным не желанием пользователя этим заниматься. :D

1 час назад, krapotkin сказал:

а почему поток должен крешить систему, я не пойму?
не нужно из потока обращаться к переменным. можно задать ему обработчик OnTerminate
конечно и форма, из которой его вызвали может перестать существовать, но тогда просто обработчик вешать на то что существовать точно БУДЕТ

Потому что единственная цель жизни потока в данном случае - обратиться к серверу с 'select тра-ля-ля' и заполнить таблицу. Таблиц на форме может быть 5-6. Соответственно потоков столько-же. Костылей наставить можно, но правильнее при закрытии формы поток прибить. Точнее под винду так и поступаю, но сейчас портирую на мобилки. И без конструкции вида

TerminateThread(ServerReader.Handle,$DEAD);

пока не представляю как это сделать.

 

Изменено пользователем Akad
Ссылка на комментарий
  • 0
8 минут назад, Akad сказал:

межпоточное взаимодействие нужно осуществлять на локах (если нужно быстро, но в дельфе нет, только через апи).

С каких пор в Delphi перестали существовать TCriticalSection, TMutex, TEvent? Которые, кстати, работают кроссплатформенно, используя штатные средства, предоставляемые ОС.

Изменено пользователем kami
Ссылка на комментарий
  • 0
26 минут назад, kami сказал:

С каких пор в Delphi перестали существовать TCriticalSection, TMutex, TEvent?

Да, они действительно существуют. Но во времена XE2 они как-то очень "странно" работали. Поэтому написал свои. Возможно сейчас ситуация стала лучше.Не проверял. Беру свои слова обратно.

Но TerminateThread в любом случае нет, а нужен он.
 

Ссылка на комментарий
  • 0
4 часа назад, Akad сказал:

'select тра-ля-ля' и заполнить таблицу.

я заполняю структуры данных, не имеющие отношения к форме, да еще и в главном потоке, так что все пучком пока.

Ссылка на комментарий

Присоединяйтесь к обсуждению

Вы можете написать сейчас и зарегистрироваться позже. Если у вас есть аккаунт, авторизуйтесь, чтобы опубликовать от имени своего аккаунта.

Гость
Ответить на вопрос...

×   Вставлено с форматированием.   Вставить как обычный текст

  Разрешено использовать не более 75 эмодзи.

×   Ваша ссылка была автоматически встроена.   Отображать как обычную ссылку

×   Ваш предыдущий контент был восстановлен.   Очистить редактор

×   Вы не можете вставлять изображения напрямую. Загружайте или вставляйте изображения по ссылке.

  • Последние посетители   0 пользователей онлайн

    • Ни одного зарегистрированного пользователя не просматривает данную страницу
×
×
  • Создать...