Sposoby wykrywania i usuwania błędów. Tomasz Borzyszkowski



Podobne dokumenty
Laboratorium Informatyka (I) AiR Ćwiczenia z debugowania

GNU GProf i GCov. przygotował: Krzysztof Jurczuk Politechnika Białostocka Wydział Informatyki Katedra Oprogramowania ul. Wiejska 45A Białystok

Zajęcia nr 1 Podstawy programowania. dr inż. Łukasz Graczykowski mgr inż. Leszek Kosarzewski Wydział Fizyki Politechniki Warszawskiej

znajdowały się różne instrukcje) to tak naprawdę definicja funkcji main.

Podstawy Programowania.

PLAN WYNIKOWY PROGRAMOWANIE APLIKACJI INTERNETOWYCH. KL IV TI 6 godziny tygodniowo (6x15 tygodni =90 godzin ),

Laboratorium 3: Preprocesor i funkcje ze zmienną liczbą argumentów. mgr inż. Arkadiusz Chrobot

Podstawy programowania. Wykład: 4. Instrukcje sterujące, operatory. dr Artur Bartoszewski -Podstawy programowania, sem 1 - WYKŁAD

Podstawy Programowania

Programowanie I. O czym będziemy mówili. Plan wykładu nieco dokładniej. Plan wykładu z lotu ptaka. Podstawy programowania w językach. Uwaga!

Bash - wprowadzenie. Bash - wprowadzenie 1/39

Wstęp do Informatyki i Programowania Laboratorium: Lista 0 Środowisko programowania

Podstawy programowania Laboratorium. Ćwiczenie 2 Programowanie strukturalne podstawowe rodzaje instrukcji

Cwiczenie nr 1 Pierwszy program w języku C na mikrokontroler AVR

Techniki programowania INP001002Wl rok akademicki 2018/19 semestr letni. Wykład 8. Karol Tarnowski A-1 p.

Testowanie oprogramowania. Testowanie oprogramowania 1/34

Tworzenie oprogramowania

Wprowadzenie do programowania w języku Visual Basic. Podstawowe instrukcje języka

Języki C i C++ Wykład: 2. Wstęp Instrukcje sterujące. dr Artur Bartoszewski - Języki C i C++, sem. 1I- WYKŁAD

Wstęp do programowania. Wykład 1

- - Ocena wykonaniu zad3. Brak zad3

PLAN WYNIKOWY PROGRAMOWANIE APLIKACJI INTERNETOWYCH. KL III TI 4 godziny tygodniowo (4x30 tygodni =120 godzin ),

Programowanie Systemów Wbudowanych

Optymalizacja programów Open Source. Profilery wysokiego poziomu część 2. Krzysztof Lichota

Visual Basic Debugging and Error Handling

1 Podstawy c++ w pigułce.

Podstawy programowania, Poniedziałek , 8-10 Projekt, część 1

Wstęp do programowania

Podstawy programowania. Wykład Funkcje. Krzysztof Banaś Podstawy programowania 1

Wstęp do Programowania, laboratorium 02

Algorytm. a programowanie -

C++ - [1-3] Debugowanie w Qt Creator

Co nie powinno być umieszczane w plikach nagłówkowych:

Języki programowania zasady ich tworzenia

Programowanie Systemów Czasu Rzeczywistego

Piotr Dwieczkowski. Code coverage. Mierzenie pokrycia kodu, teoria oraz praktyka w C/C++

Myśl w języku Python! : nauka programowania / Allen B. Downey. Gliwice, cop Spis treści

Programowanie Proceduralne

Języki formalne i techniki translacji

Testowanie oprogramowania

1.Wstęp. 2.Generowanie systemu w EDK

Automatyzacja kompilacji. Automatyzacja kompilacji 1/28

Schematy blokowe I. 1. Dostępne bloki: 2. Prosty program drukujący tekst.

Klasa 2 INFORMATYKA. dla szkół ponadgimnazjalnych zakres rozszerzony. Założone osiągnięcia ucznia wymagania edukacyjne na. poszczególne oceny

Nazwa wariantu modułu (opcjonalnie): Laboratorium programowania w języku C++

Programowanie w elektronice: Podstawy C

Wykaz zmian w programie WinAdmin Replikator

Algorytmika i programowanie usystematyzowanie wiadomości

Podstawy programowania. Wykład: 9. Łańcuchy znaków. dr Artur Bartoszewski -Podstawy programowania, sem 1 - WYKŁAD

3. Podaj elementy składowe jakie powinna uwzględniać definicja informatyki.

Instrukcja laboratoryjna cz.0

ECDL Podstawy programowania Sylabus - wersja 1.0

1. Pierwszy program. Kompilator ignoruje komentarze; zadaniem komentarza jest bowiem wyjaśnienie programu człowiekowi.

Systemy Operacyjne - Operacje na plikach

do instrukcja while(wyrażenie);

Tworzenie oprogramowania

Katedra Elektrotechniki Teoretycznej i Informatyki. wykład 12 - sem.iii. M. Czyżak

Narzędzia informatyczne w językoznawstwie

Laboratorium 1 Temat: Przygotowanie środowiska programistycznego. Poznanie edytora. Kompilacja i uruchomienie prostych programów przykładowych.

Programy użytkowe (utilities)

Skrypty i funkcje Zapisywane są w m-plikach Wywoływane są przez nazwę m-pliku, w którym są zapisane (bez rozszerzenia) M-pliki mogą zawierać

Programowanie w języku C++ Grażyna Koba

Przykładowe sprawozdanie. Jan Pustelnik

Temat: Dynamiczne przydzielanie i zwalnianie pamięci. Struktura listy operacje wstawiania, wyszukiwania oraz usuwania danych.

Zadanie programistyczne nr 3 z Sieci komputerowych

Poprzedni wykład [ ] :

Podstawy programowania. Wykład 9 Preprocesor i modularna struktura programów. Krzysztof Banaś Podstawy programowania 1

Zadania: 1. Funkcja przeliczająca F na C: float FtoC(float f){ return (f 32.0) * 5.0 / 9.0; }

IBM SPSS Statistics - Essentials for R: Instrukcje instalacji dla Linux

Laboratorium nr 4: Arytmetyka liczb zespolonych

Szablony funkcji i klas (templates)

Testowanie II. Celem zajęć jest zapoznanie studentów z oceną jakości testów przy wykorzystaniu metryk pokrycia kodu testami (ang. code coverage).

Jeśli chcesz łatwo i szybko opanować podstawy C++, sięgnij po tę książkę.

Podstawowe elementy proceduralne w C++ Program i wyjście. Zmienne i arytmetyka. Wskaźniki i tablice. Testy i pętle. Funkcje.

Wyrażenie include(sciezka_do_pliku) pozwala na załadowanie (wnętrza) pliku do skryptu php. Plik ten może zawierać wszystko, co może się znaleźć w

1 Zapoznanie się ze środowiskiem Xenomai.

Program szkoleniowy. 24 h dydaktycznych (18 h zegarowych) NAZWA SZCZEGÓŁY CZAS

Temat 1: Podstawowe pojęcia: program, kompilacja, kod

Programowanie Strukturalne i Obiektowe Słownik podstawowych pojęć 1 z 5 Opracował Jan T. Biernat

System operacyjny Linux

Zad. 5: Układ równań liniowych liczb zespolonych

W przeciwnym wypadku wykonaj instrukcję z bloku drugiego. Ćwiczenie 1 utworzyć program dzielący przez siebie dwie liczby

Warsztaty dla nauczycieli

1 Przygotował: mgr inż. Maciej Lasota

Podstawy Informatyki. Algorytmy i ich poprawność

Programowanie mikrokontrolerów AVR

Bardzo krótki kurs Perla

1 Podstawy c++ w pigułce.

Programowanie proceduralne INP001210WL rok akademicki 2017/18 semestr letni. Wykład 7. Karol Tarnowski A-1 p.

Pakiety i interfejsy. Tomasz Borzyszkowski

Wykład 15. Literatura. Kompilatory. Elementarne różnice. Preprocesor. Słowa kluczowe

Trochę o plikach wsadowych (Windows)

Efektywna analiza składniowa GBK

1. Nagłówek funkcji: int funkcja(void); wskazuje na to, że ta funkcja. 2. Schemat blokowy przedstawia algorytm obliczania

Nazwa implementacji: Nauka języka Python pętla for. Autor: Piotr Fiorek

Wykaz zmian w programie SysLoger

Podstawy programowania - 1

Wyjątki. Streszczenie Celem wykładu jest omówienie tematyki wyjątków w Javie. Czas wykładu 45 minut.

Transkrypt:

Sposoby wykrywania i usuwania błędów Tomasz Borzyszkowski

Mylić się jest rzeczą ludzką Typy błędów: błędy specyfikacji: źle określone wymagania błędy projektowe: nieodpowiednie struktury danych i algorytmy błędy kodu: powstają na etapie realizacji projektu przy pomocy wybranego narzędzia programistycznego Etapy debugowania, poprawiania programu: testowanie: znalezienie błędu lokalizacja: zidentyfikowanie błędnego kodu korekta: poprawienie błędu weryfikacja: sprawdzenie czy poprawka działa Program z błędem: W pliku debug1.c znajduje się funkcja sort, która ma sortować struktury typu item metodą bąbelkową. Niestety po uruchomieniu otrzymujemy błąd segmentacji. 2

Sposoby testowania Przeglądanie kodu Podstawowym sposobem wykrywania błędów jest przeglądanie kodu. Najlepiej, gdy nasz kod przejrzy inna osoba. Do wykrywania błędów składniowych możemy użyć kompilatora: gcc -Wall -pedantic -ansi -o debug1 debug1.c Oprzyrządowanie kodu Oprzyrządownie polega na dodawaniu nowego kodu do testowanego programu w celu zebrania jak największej liczby informacji o programie. Wykorzystuje się do tego preprocesor C, pozwalający decydować podczas kompilacji, czy dołączyć kod wykorzystywany do debugowania. Np.: #ifdef DEBUG printf("debug: x=%d\n", x); #endif powyżej printf wykona się, gdy program będzie skompilowany z opcją -DDEBUG. Patrz debug2.c 3

Sposoby testowania cd Oprzyrządowanie kodu bez ponownej kompialcji Wadą poprzedniego rozwiązania była konieczność ponownej kompilacji przed każdym debugowaniem. Alternatywnymi sposobami umożliwiania debugowania kodu przez użytkownika są: Obsługa przez debugowany program opcji -d podawanej z linii komend (trzeba ją oprogramować samemu) Użycie w programie możliwości rejestracji zachowania programu przez funkcję syslog (patrz man 3 syslog) Program gdb gdb jest programem umożliwiającym śledzenie wykonywania innych programów. Śledzony program powinien być skompilowany z opcją -g by do kodu wynikowego dołączyć informacje istotne dla debugera. gcc -g -o debug3 debug3.c gdb debug3 komenda (gdb) help wyświetla dostępne komendy (patrz: man gdb i info gdb). 4

Program gdb gdb uruchamianie Rozpoczynamy wykonanie programu komendą (gdb)run. Argumenty polecenia (gdb)run zostaną przekazane testowanemu programowi. W naszym przypadku pojawi się błąd segmentacji wraz z linią, w której po raz pierwszy ten błąd wystąpił. gdb śledzenie stosu Komenda (gdb)backtrace pozwala śledzić stos wywołań aż do miejsca, w którym jesteśmy. Używane do programów z większą liczbą wywołań podprogramów i funkcji. gdb badanie zmiennych Wypisywania wartości zmiennych: (gdb)print zmienna. Rezultaty są przechowywane w pseudozmiennych $<liczba>, ostatni rezultat to $, a przedostatni $$. Sprawdzamy (gdb)print j, problem sprawiło: a[4]=a[4+1]. Spróbuj: (gdb)print a[$-1].klucz lub print a[3] (gdb)print a[$-1] 5

Program gdb cd gdb listing programu Polecenie (gdb)list wypisuje fragment programu wokół bieżącej pozycji. Widzimy, że zmienna j nie powinna przyjmować wartości 4. Zmieńmy więc linię 23. na następującą: /* 23 */ for( j=0; j<n-1; j++ ) { Po kompilacji i uruchomieniu (patrz debug4.c) program działa ale wynik nie jest niepoprawny. Sprawdźmy co robi w trakcie dziłania. gdb puntky przerwania gdb posiada komendy pozwalającę wstawiać i kontrolować tzw. punkty przerwania. Zobacz (gdb)help breakpoint. My wstawimy punkt przerwania w linii 21.: (gdb)break 21 uruchomimy program (gdb)run. Program zatrzyma się w na linii 21. Wypisujemy stan tablicy: (gdb)print tablica[0]@5 i kontynuujemy do natępnego przerwania (gdb)cont. 6

Program gdb jeszcze Wypisanie stanu tablicy za każdym razem, gdy program się zatrzyma: (gdb)display tablica[0]@5. Używając komendy (gdb) commands. ustalamy, że program ma wykonać cont za każdym razem, gdy dojdzie do bieżącego punktu przerwania. Analiza zachowania programu doprowadza nas do wniosku, że zewnętrzna pętla nie wykonuje się tyle razy ile powinna. Podejrzewamy, że winna temu jest linia 31. Spróbujmy to sprawdzić. gdb łatanie Łatą nazywamy kod, który musimy dodać do programu aby działał poprawnie. Stosując punkty przerwania możemy sprawdzić łatę zanim zmienimy kod źródłowy. Wyłączamy poprzednio ustawiony punkt przerwania i związane z nim wyświetlanie: (gdb)disable break 1 i (gdb)disable display 1. Ustawiamy przerwanie w linii 31. i kojarzymy z nim komendy: set variable n = n+1 i cont. Po uruchomieniu program zadziała poprawnie. 7

Program patch Dystrybucja nowych wersji programów jest kłopotliwa (zwłaszcza, gdy dostarczamy wersje binarne). Oprogramowanie typu Open Source znacznie ułatwia dystrybucję nowych wersji. Zamiast udostępniać nową wersję w pełnej (wielo-mb) postaci, udostępnia się jedynie różnice pomiędzy wersjami. Program diff służy do tworzenia plików zawierających różnice między źródłami wersji. diff plik1.txt plik2.txt > ró?nice.txt Łatanie programu, tj. uaktualnianie źródeł można wykonać tak: patch plik1.txt ró?nice.txt Odwracanie tego procesu: patch -R plik1.txt ró?nice.txt Zadania: 1. Zrobić łatę/łaty dla przykładu z gdb 2. Zrobić łatę do programu składającego się z wielu plików - uwzględnić łatanie w pliku Makefile 8

Testy pokrycia Jedynym sposobem potwierdzenia poprawności programu jest udowodnienie, że dla każdej możliwej wartości danych wejściowych program zwraca poprawny wynik. Dla większości programów, z wyjątkiem najprostszych, jest to zadanie tak skomplikowane, że praktycznie jest niewykonalne. Kompromisem nieograniczającym zakresu testów są tzw. testy pokrycia. Idea testów pokrycia polega na próbie oszacowania, jaka część kodu została wykonana podczas testów. Jeżeli w czasie testów wykonana została każda część programu, ich wyniki uznamy za bardziej godne zaufania. Istnieją trzy rodzaje testów pokrycia: Pokrycie instrukcji Pokrycie rozgałęzień programu Pokrycie danych 9

Pokrycie instrukcji Pokrycie instrukcji polega na sprawdzeniu czy podczas testów została wykonana każda linijka programu. Pokrycie instrukcji ma wadę: nie bierze się w nim pod uwagę wzajemnego oddziaływania części programu. Przykład: 1 :int f(int a,int b){ 2 : int r = 1; 3 : if(a>0){ 4 : r = 0; 5 : }; 6 : if(b>0){ 7 : r = 3/r; 8 : } 10: return r; 11:} Linie 1, 2, 3, 6 i 10 są testowane zawsze. Aby pokryć linię 4 należy przetestować f(1,0), natomiast by pokryć linię 7, f(0,1). Teraz nasz test pokrywa już wszystkie instrukcje programu. Co się jednak stanie gdy sprawdzimy wywołanie f(1,1)? Ze względów formalnych należy także przetestować f(0,0). 10

Pokrycie rozgałęzień i danych Test pokrycia rozgałęzień programu polega na rozważeniu wszystkich możliwych ścieżek działań programu. Liczba możliwych ścieżek programu znacznie wzrasta w miarę dodawania pętli i instrukcji warunkowych. Powoduje to także wzrost liczby testów do ich pełnego pokrycia. Test pokrycia danych obejmuje testowanie każdej możliwej kombinacji użytych danych. Istnieje kilka narzędzi do badania stopnia pokrycia badanego programu za pomocą przeprowadzonych testów. Narzędzia te pracują na zasadzie zwbogacania testowanego programu w trakcie kompilacji. Dodatkowy kod służy do gromadzenia informacji o tym, które instrukcje były wykonywane i jak często. Ponieważ narzędzia te działają na poziomie instrukcji, kod programu powinien być tak napisany by każda linia zawierała najwyżej jedną istrukcję. Złym rozwiązaniem jest umieszczanie instrukcji warunkowej w jednej linii lub stosowanie makr zawierających wyrażenia warukowe. 11

Narzędzie gcov gcov jest narzędziem do testowania pokrycia instrukcji programu. Aby korzystać z gcov, należy przygotować specjalną wersję badanej aplikacji (podobnie jak dla gdb). Do przygotowania kodu musimy użyć kompilatora C w wersji GNU ze specjalnymi opcjami linii poleceń: -fprofile-arcs zmusza kompilator do umieszczania w testowanym programie dodatkowego kodu, pozwalającego rejestrować, która instrukcja jest wykonywana. Informacja taka będzie zapisywana w pliku o nazwie takiej jak plik źródłowy z końcówką.da -ftest-coverage prócz pliku z kodem obiektowym (.o) powstaną pliki o końcówkach.bb i.bbg, zawierające zapis struktury rozgałęzień kodu źródłowego. Używane są przez gcov do tworzenia mapy działania programu. -fbranch-probabilities opcja ta powoduje optymalizację śledzenia rozgałęzień. 12

Narzędzie gcov przykład W katalogu testy znajduje się przykładowa aplikacja obliczająca wyrażenia arytmetyczne zadane w Odwrotnej Notacji Polskiej. Aplikacja składa się z kilku plików zawierających funkcje zewnętrzne, pliku Makefile oraz plików test[0-6] zawierających testowe wyrażenia. Przykładowy przebieg testów: Kompilacja aplikacji: $ make Wykonanie testów: $ make test Wykonanie analiz pokrycia: $ make gcov Wykonanie kasowania liczników: $ make clean_da Analizując testy aplikacji należy szczególną uwagę zwrócić na: Opcje polecenia gcov Wpływ plików *.da na zawartość plików *.c.gcov Analizę rozgałęzień kodu (patrz opcja -b polecenia gcov i instrukcje rozgałęziające: if, case, for, while) 13

Testowanie wydajności Ważnym aspektem testowania jest wydajność. Aplikacja prócztego, że musi działać poprawnie musi być użyteczna, czyli oddawać wyniki w rozsądnym czasie. Stąd ważne jest znajdowanie w programie takich miejsc, w których traci się najwięcej czasu. Narzędziem, które może nam pomóc w testowaniu wydajności jest gprof. Aby przygotować kod programu dla gprof należy go skompilować z opcją -pg, następnie uruchomić program i po nim wywołać gprof z nazwą programu. Przykładowe wywołania w plikach Makefile w katalogach testy i testy2. Po uruchomieniu programu powstaje plik gmon.out, zawierający zapis profilu działania. Program w trakcie działania zapisał w nim wyniki pomiarów czasu spędzonego w każdej z funkcji. Program gprof może gromadzić dane z wielu uruchomień badanego programu. Aby skorzystać z tej możliwości, należy użyć opcji -s w wywołaniu gprof. Informacja o profilu będzie wówczas gromadzona w pliku gmon.sum. 14