Od wielu dni ciężko walczę (ale na próżno) z maskami wyjątków.Maskowanie wyjątków w Delphi
Opracowałem aplikację, która wykonuje obliczenia z dużą liczbą obliczeń zmiennoprzecinkowych na setkach tysięcy rekordów. Oczywiście kod musi obsługiwać wyjątki, szczególnie te związane z obliczeniami zmiennoprzecinkowymi: Overflow, ZeroDivide, itp.
Aplikacja działa poprawnie pod Windows 7 (32bit lub 64bit) z wieloma różnymi typami procesorów, jeśli błąd występuje, gdy warunek jest prawidłowo obsługiwany, wyjątek jest zgłaszany, a rekord jest odrzucany.
Niestety, problemy pojawiają się, gdy uruchamiam aplikację w miejscu, w którym ma działać: na dedykowanym serwerze z procesorem Intel Xeon E5-2640 v2 i systemem Windows Server 2003 R2. W tym miejscu wyjątki nie zostały podniesione: zapisy z błędami nie są odrzucane, a zatem wyniki są zanieczyszczane przez te wartości liczbowe, z którymi maszyna przedstawia +INF
lub .
Problemem jest to, że na serwerze ustawienia domyślne maskowania błędów różnią się od tych, które znajdziemy w Windows 7. W szczególności, wywołując procedurę GetExceptionMask
na serwerze domyślnie znajdę exZeroDivide
natomiast jeśli wywołanie GetExceptionMask
na Windows 7 ten wyjątek nie jest maskowany. Rezultatem jest to, co powiedziałem: uruchamiając aplikację na serwerze te wyjątki nie są wywoływane, lecz przetwarzane przez procesor zwracający ekstremum i "zanieczyszczające" wartości liczbowe.
OK, nie wpadaj w panikę, mówię, po prostu dzwonisz (to jest w sekcji inicjującej) SetExceptionMask
z wyjątkiem exZeroDivide
, ale to nie działa. Lub lepiej, chociaż zaraz po wywołaniu SetExceptionMask
wyjątek exZeroDivide
nie jest już maskowany, gdy wykonywany jest kod z obliczeniami zmiennoprzecinkowymi, zbiór TArithmeticExceptionMask
zwrócony przez GetExceptionMask
nadal zawiera exZeroDivide
, a więc w przypadku wystąpienia błędu wyjątek nie zostanie zgłoszony.
Czy ktoś może mi powiedzieć, jaki jest prawidłowy sposób wywołania SetExceptionMask
?
Jaki jest powód, dla którego domyślne ustawienie maskowania może się różnić od komputera i innego? system operacyjny lub typ procesora?
Dzięki.
To jest dobry opis, ale czy możesz opublikować przykładowy kod, który generuje wyjątek, i próbkę, aby pokazać, jak próbujesz uporać się z maskowaniem? To znacznie ułatwi nam znalezienie rozwiązania. :) –
Zgadzam się, trudno powiedzieć, nie widząc, jak to robisz. Sugeruję uruchomienie zupełnie nowej aplikacji testowej, która powieli to zachowanie i udostępni nam ten kod. –
Wygląda na to, że coś jest wprowadzane do procesu na serwerze 2003 - sprawdzanie wirusów, globalne przechwytywanie, inne narzędzie do monitorowania systemu? - który ustawia słowo flagowe FP z niepoprawnymi wartościami. –