Teraz, kiedy popełniam błąd programistyczny ze wskaźnikami w C, dostaję ładny błąd segmentacji, mój program ulega awarii, a debugger może nawet powiedzieć mi, gdzie poszło źle.
Jak to zrobili, skoro ochrona pamięci nie była dostępna? Widzę, jak programiści DOS bawią się i psują cały system operacyjny, gdy popełnił błąd. Wirtualizacja nie była dostępna, więc mógł jedynie uruchomić się ponownie i spróbować ponownie. Czy to naprawdę tak wyglądało?
Odpowiedzi:
Tak, prawie tak się stało. W większości systemów, które miały mapy pamięci, lokalizacja 0 była oznaczona jako niepoprawna, dzięki czemu wskaźniki zerowe mogły być łatwo wykryte, ponieważ był to najczęstszy przypadek. Ale było wiele innych przypadków, które spowodowały spustoszenie.
Ryzykując, że zabrzmi to jak geezer, powinienem zauważyć, że obecnie skupianie się na debugowaniu nie należy do przeszłości. Wcześniej dużo starano się pisać poprawne programy, zamiast usuwać błędy z niewłaściwych programów. Po części dlatego, że taki był nasz cel, ale w dużej mierze dlatego, że narzędzia utrudniały pracę. Spróbuj pisać swoje programy na papierze lub na perforowanych kartach, a nie w IDE i bez korzyści interaktywnego debuggera. Daje smak poprawności.
źródło
Kiedyś nie mieliśmy ochrony pamięci i całego tego cholernego biznesu! Użyliśmy printf, aby określić, gdzie jesteśmy w programie, i podobało nam się !
Choć z całą powagą, zwykle oznaczało to, że byliśmy bardziej ostrożni. Tam, gdzie nazywa się malloc, gdzieś w programie musiał być darmowy, a takie sprawdzanie było rygorystyczne, ponieważ w przypadku problemu, jak wyraźnie zauważyłeś, błędy segmentacji nie są pomocnymi błędami.
W przypadku takich błędów najlepiej jest spróbować zrozumieć, kiedy występują takie błędy segmentacji (za pomocą printf) i, patrząc na kod, ustalić, dlaczego dostęp do pamięci w tym momencie nie był prawidłowy i stamtąd działać wstecz.
Zasadniczo to samo dzieje się dzisiaj, z wyjątkiem tego, że używamy debugerów do ustalenia, kiedy wystąpią błędy, ale nadal musisz zrozumieć, dlaczego tak się stało, i nie zawsze jest to tak proste, jak znalezienie linii, w której wystąpił błąd. Błędy powodują błędy, takie jak reakcja łańcuchowa, a jeśli byłeś programistą C w tamtych czasach, spędziłeś 20% czasu na kodowaniu, a resztę czasu wyciągałeś włosy, naprawiając błędy.
źródło
dobrze ..
segfault to naprawdę fajny wskaźnik, że coś jest nie tak, ale nadal musisz znaleźć podstawową przyczynę. Więc jeśli zadajesz pytanie, jak znaleźć podstawową przyczynę, odpowiedź nie różni się dzisiaj tak bardzo jak wtedy. Oczywiście języki i narzędzia stały się łatwiejsze w obsłudze, ale ogólny taktik jest taki sam:
Na bardziej abstrakcyjnym poziomie masz trzy podejścia: 1. praca z kodem 2. spójrz na program podczas działania 3. spójrz na wyniki po tym, jak zrobił coś głupiego
przy okazji błąd wskaźnika nie musi powodować awarii.
Jako programista Amigi wykorzystałem prawie wszystko. I tak rozpoczyna się tam, gdzie powszechna praktyka.
źródło
Na IBM 360 z uruchomionymi zadaniami wsadowymi Fortran otrzymywaliśmy zrzuty heksadecymalne. Taki zrzut może wynosić nawet cal grubości zielono-białego papieru do drukarek składanego na wachlarz. Informuje o tym, jakie są rejestry, i stamtąd możemy cofnąć się i dowiedzieć się, co robi program. Możemy znaleźć każdy podprogram i dowiedzieć się, gdzie zachował swój adres zwrotny, abyśmy mogli zobaczyć kontekst. Pomogłoby to mieć listę asemblerów programu.
źródło
Kiedyś pracowałem nad naprawą błędów w znanym wówczas oprogramowaniu do prezentacji Windows 3.1.
Miałem błąd, który, gdy się pojawił, spowodował niebieski ekran śmierci.
Błąd wystąpił tylko wtedy, gdy pewna pętla została wykonana ponad 1000 razy. Użyłem zaawansowanych funkcji debuggera, aby pozwolić punktowi przejścia przejść 1000 razy, a następnie ostrożnie przeszedłem program. Za każdym razem, gdy szedłem za daleko lub pomijałem wywołanie funkcji, które zawierało błąd Windows Blue Screened.
W końcu po kilku dniach pracy zawęziłem ją do funkcji, której kończy się pamięć i zamiast wyświetlać komunikat o błędzie, dołączyłem komunikat o błędzie do bufora. Z każdą kolejną iteracją tracił więcej pamięci, aż coś kluczowego zostało nadpisane i system Windows został zniszczony.
Rozwiązaniem były umiejętności debugowania i wytrwałość.
źródło