[C++] Operacje na wskaźniku - kiedy standard określa niezdefiniowane zachowanie?
Ostatnio zmodyfikowano 2015-01-05 21:52
DejaVu |
» 2015-01-03 21:35:08 @Kaikso: Wróćmy do punktu wyjścia - czy kod operujący na podanym wskaźniku zadziała poprawnie patrząc z punktu widzenia standardu? My przytoczyliśmy całą masę argumentów, że NIE więc te dywagacje na temat ifdefowania kodu i dodawania #warning-ów nic nie zmienia, bo najpierw programista musi być świadom, że pisze ZŁY kod. Jak nie będzie tego świadom (patrz: omawiany przykład) to nie ma szans na to by jakikolwiek #warning się pojawił w jakimkolwiek słusznym miejscu. |
|
Kaikso |
» 2015-01-03 21:40:58 Eh właściwie tak, samo wyrażenie jest nieprzewidywalne, ale cały kod na żadnej platformie nie zostanie błędnie zinterpretowany, aby tak się stało kompilator musiałby być niezgodny ze standardem. Problemem tu jest wewnętrzna niezgodność standardu :P |
|
DejaVu |
» 2015-01-03 21:47:08 @Kaikso: Przecież podałem Ci przykład kiedy omawiana aplikacja zachowa się niepoprawnie... nie rozumiem czemu upierasz się, że jest ten kod jest okej. Jeżeli masz takie wewnętrzne przekonania, że wszystko jest z nim w porządku - spoko. Proszę tylko nie propaguj informacji błędnych, bo później n-set osób zacznie powtarzać Twoje niesłuszne racje uważając, że Twoja prawda jest dla nich wygodniejsza i bliższa ich tokowi myślenia. Chcesz dostarczyć kontrargumentów - przytocz odpowiedni fragment standardu na poparcie Twoich twierdzeń. Problemem tu jest wewnętrzna niezgodność standardu :P
|
Z błędnych założeń zawsze mogą wychodzić zdania prawdziwe. Wskaż niezgodności w standardzie jeżeli takowe znalazłeś. Chętnie je umieszczę w jakimś zacnym artykule co by zwiększyć świadomość programistów o zagrożeniach wynikających z treści standardu. |
|
Kaikso |
» 2015-01-03 21:51:25 Wyrażenie, a nie cały kod. Zmienna tekst wskazuje na ciąg o długości większej od 0. Nigdy nie otrzymamy w całym wyrażeniu adresu znajdującego się poza granicami. Chyba że ktoś podmieni adres lub strlen.
Co do trzymania się standardu, to jest to niewykonalne biorąc pod uwagę niezgodność bibliotek i kompilatorów. |
|
DejaVu |
» 2015-01-03 21:54:07 Nigdy nie otrzymamy w całym wyrażeniu adresu znajdującego się poza granicami.
|
A widziałeś kiedyś, aby procesor potrafił sumować n-liczb naraz? Procesor dostaje osobno operację odejmowania i osobno operację dodawania. Tym samym wychodzisz poza dopuszczalne granice. |
|
Kaikso |
» 2015-01-03 22:06:09 1.) char tekst[] = "kolorowo"; - mamy zmienną wskaźnika `tekst' - przypisujemy jej adres stałego ciągu "kolorowo" (różny od zera) 2.) *( tekst - 1 + strlen( tekst ) ) - obliczamy wartość tymczasową tekst - 1 ( tekst != 0 => tekst - 1 >= 0 ) - wartość tymczasową zwiększamy o długość tekstu - sprawdzamy wartość pod otrzymanym adresem I w którym miejscu wyjdziemy poza zakres ? |
|
DejaVu |
» 2015-01-03 22:08:33 @up: przeczytaj post P-124007 z trzeciej strony tego tematu - tam masz wykazane, że wiersz ma niezdefiniowaną operację. Wystarczy, że kompilator przypisze adres zmiennej do jednego rejestru, offsety zacznie liczyć na drugim rejestrze, pilnując jednocześnie, że wartość nie może wyjść poza zakres, a tak się w Twoim przypadku dzieje. /edit: - obliczamy wartość tymczasową tekst - 1 ( tekst != 0 => tekst - 1 >= 0 )
|
Tu właśnie popełniasz kardynalny błąd. Zakładasz, że ta operacja wykona się w ramach jednego rejestru. |
|
Kaikso |
» 2015-01-03 22:10:30 Jeśli by tak robił to wiele innych zapisów, z musu zgodnych ze standardem było by nieprawidłowych.
@Down: rozumiem niezgodność ze standardem, ale w praktyce wygląda to inaczej. |
|
1 2 3 « 4 » 5 6 7 8 |