Elektroda.pl
Elektroda.pl
X
Elektroda.pl
MetalWork SafetyMetalWork Safety
Please add exception to AdBlock for elektroda.pl.
If you watch the ads, you support portal and users.

Debuger jako narzędzie marnujące czas programisty?

trol.six 19 Jul 2018 13:26 2649 58
  • #31
    tplewa
    Level 38  
    @trol.six

    Ja ci powiem tak nie da się odpowiedzieć na te pytania... to jak byś chciał odpowiedzieć na pytanie czy samochód jest potrzebny ;) Można pisać kod bez debugera i wiele lat tak się robiło bo po prostu procki nie miały interfejsu do debugowania... lub zjadał on znaczną część IO i się z niego rezygnowało. Wtedy za zwyczaj kombinowało się z jakąś inną formą debugowania (wysyłanie danych przez UART itp.). W jednym urządzeniu gdzie procek nie miał takiej możliwości, a procek sterował OSD to i na OSD się wyświetlało dane ułatwiające debugowanie...

    Niewątpliwie jest to narzędzie ułatwiające pracę, ale na upartego można się bez niego obejść. W zasadzie im większy program tym większa szansa że popełnimy jakieś błędy, a debuger pozwoli często szybciej je wykryć. Kolejna sprawa debuger debugerowi nie równy...

    Czasami mamy też jakieś problemy które i z debugerem trudno rozwiązać (albo przydał by się o większych możliwościach).
  • MetalWork SafetyMetalWork Safety
  • #32
    tmf
    Moderator of Microcontroller designs
    Jeżeli chcesz komuś udowodnić, że da się pisać programy bez używania debuggera, to tak, da się. Da się go zastąpić pisząc programy testowe, analizując każdą linię kodu dziesiątki razy, korzystając np. z assertów itd. Podobnie jak da się pisać programy nie korzystając z IDE, czy zapisywać je bezpśrednio w postaci binarnej. Chodzi o to, że jak każde narzędzie, także debugger, ma nam ułatwiać życie. I ułatwia. Tylko, żeby to poznać musisz zacząć go używać. Bo piszesz troche tak, jak ktoś kto używa wyłącznie śrubokręta i zastanawia się po co ludzie wymyślili wkrętarkę. Jakkolwiek korzystanie z niej nie jest obowiązkowe, to po prostu często ułatwia życie. Z debuggerem jest podobnie. Sam zresztą pokazujesz przykłady:
    trol.six wrote:
    Freddie Chopin napisał:
    https://gcc.gnu.org/bugzilla/show bug.cgi?id=83703
    https://stackoverflow.com/ques...dd-floating-point-inaccuracies
    Naprawdę potrzebny jest do tego debuger?


    Nie jest potrzebny, ale pomyśl. Piszesz program, który daje dziwne wyniki (niezgodne z oczekiwaniem). Czy prościej jest teraz analizować cały sposób przetwarzania danej zmiennej, czy np. sobie prześledzić jedną instrukcję i zauważyć, że po przemnożeniu wynik jest inny niż spodziewany? Przechodzę na asembler, widzę, że instrukcja FPU ma prawidłowe argumenty, ale daje nieprawidłowy wynik. Wniosek? Nawet głupi błąd typu == dla float. Ile osób nie zauważy tego problemu? W debuggerze od razu widzę, że porównuję np. 0.9999999 z 1.00000001 i już mi się czerwone światełko zapala.
    trol.six wrote:
    tmf napisał:
    Często w wyniku błędu program sypie się w miejscu nie mającym ze źródłem błędu nic wspólnego

    W zasadzie chyba tylko w przypadku nadpisania danych, czy stosu. Zdarzyło mi się i uważam że to moja wina że nie napisałem sobie sprawdzenia zakresu w kodzie. Takie sprawdzenie można albo dać na zawsze w kodzie, albo doraźnie stosować np


    Nadpisanie pamięci to typowy przykład. Tu debugger ma przewagę bo sobie zastawiam pułapkę i widzę każdy zapis lub odczyt z danego obszaru. Więc wykrycie sytuacji w której np. stos nadpisuje zmienne jest raczej proste. Oczywiście mogę to zrobić bez debuggera również, tyle, że już tak proste to nie będzie. Ale tego typu błędy są częstsze. Np. wynik jakiejś funkcji jest nieprawidłowy. Ten wynik jest przetwarzany przez kilka kolejnych funkcji, a jdopiero któraś kolejna się wysypuje bo dostaje argument spoza zakresu. I teraz szukaj, gdzie problem wystąpił, bo widzisz tylko skutek problemu, a nie co jest jego źródłem.
    trol.six wrote:
    tmf napisał:
    Podglądam program w trakcie wykonania i widzę, że wartość zmiennej odbiega od założonej, lub warunki które wydawało mi się, że są ok, nagle powodują, że program wchodzi w sekcje, w które nie powinien

    Do takich rzeczy używam programu testowego. Bo zmiennych czasem jest kilka, czasem kilkadziesiąt i nie wiadomo która kiedy źle się zmieni.

    No widzisz, czyli zamiast zastosować proste rozwiązanie, wymyślasz jakieś kosmiczne obejście. Czy prościej jest sobie zrobić breakpointa i podglądnąć wartość zmiennej, czy napisać specjalny program testowy? Oczywiście, czasami się łączy te metody, też często np. daje fragmenty w programie, które wypluwają mi efekty pracy programu przez UART, niemniej potem przechodzę na debugger, aby lepiej wyizolować problem.
    trol.six wrote:
    tmf napisał:
    Debugger ułatwi ci wychwycenie problemu polegającego np. na nieprawidłowej modyfikacji bitów - np. zapis PORT= zamiast PORT|=

    Takie błędy można wyszukać automatycznie za pomocą linii poleceń np:

    Tu nie wiem, czy piszesz to na poważnie? Co mi da wygrepowanie miejsc w których jest ten kod? Gdyby zapis |= był zawsze zły to ok, ale tu oba mogą być poprawne więc wymaga to większej analizy. W większym programie takie wyszukiwanie zwróci mi od kilkuset do kilku tysięcy linii kodu, więc to kompletnie nic nie daje. Poza tym pisze o pewnej klasie błędów. Kolejnym przykładem jest np. = zamiast ==, lub vice versa i podobne. Ludzie często godzinami ślęczą nad kodem szukając takich błędów. I tu możliwość debugowania bardzo się przydaje.

    trol.six wrote:
    tmf napisał:
    Debugger umożłiwia wychwycenie wielu głupich błędów, które normalnie się nie widzi patrząc na kod.

    Jak nie widze błędu, ide na piwo. ;)

    To załóż temat o wyższości piwa nad debuggerem :)
  • #33
    User removed account
    User removed account  
  • #34
    Freddie Chopin
    MCUs specialist
    trol.six wrote:
    To może pytanie, czy debugerem moge zastawiać pułapki na dostęp do zmiennych?

    Oczywiście.

    trol.six wrote:
    Naprawdę potrzebny jest do tego debuger?

    Do wyizolowanego przypadku oczywiście nie jest. W dużym programie takie błędy są zwykle propagowane przez 10 warstw obejmujących z 15 plików. I wtedy tak naprawdę nie wiesz gdzie jest problem, z którą ścieżką, z którymi obliczeniami - wiesz tylko, gdzie się ten problem objawia i być może wiesz jak go wywołać. Uprzedzając to co napiszesz - tak, można sobie to "printf-ować", tyle że owe "printf-owanie" to taki właśnie "debugger-dla-ubogich". Czasami nie ma na co "printf-ować (albo musiałbyś się najpierw przylutować do jakichś pinów na PCB), wiec wtedy też ta opcja odpada.

    Temat jest nieco zabawny, bo generalnie debugger oczywiście nie jest do niczego potrzebny. Tak samo jak programowanie, elektronika, mikrokontrolery, nowoczesna cywilizacja itd. - faktycznie potrzebne jest tylko słońce, tlen, jedzenie i woda. Reszta to w mniejszym lub większym stopniu fanaberie.

    Swoją drogą do znajdowania błędów w kompilatorze też się debugger przydaje, bo bez niego na logikę nie dojrzysz niczego. Powodem jest to, że błędy kompilatora wykluczają zastosowanie reguł języka, które po prostu wtedy nie obowiązują. Bez debuggera szukasz igły w stogu siana, z debuggerem możesz - bez rekompilacji i zmiany kodu - podglądać co chcesz i gdzie chcesz.

    trol.six wrote:
    A teraz zmień sobie coś w kodzie i co? Znowu będziesz bawić się debugerem? Piszesz test. A jak masz test uruchamiasz automatycznie za każdym razem.

    Czyli tak jak wspomniano wcześniej - w idealnym świecie oczywiście debugger jest zupełnie zbędny.

    Dodano po 6 [minuty]:

    tmf wrote:
    Kolejnym przykładem jest np. = zamiast ==, lub vice versa i podobne. Ludzie często godzinami ślęczą nad kodem szukając takich błędów. I tu możliwość debugowania bardzo się przydaje.

    Kiedyś chyba przed dłuższy czas szukałem błędu, którym w końcu okazał się ten mały wkurzający znaczek średnika. Coś na styl:

    Code:
    while(cośtam == ileśtam);
    
    {
      tutajCośZrób();
    }


    Gdy w końcu dotarłem do źródła, to na debuggerze od razu było widać, że przeskakuje przez pętlę i dopiero wtedy minęła mi selektywna ślepota.
  • MetalWork SafetyMetalWork Safety
  • #35
    grko
    Level 33  
    Freddie Chopin wrote:

    Gdy w końcu dotarłem do źródła, to na debuggerze od razu było widać, że przeskakuje przez pętlę i dopiero wtedy minęła mi selektywna ślepota.


    No jeden log również by załatwił sprawę. Naprawdę, niekiedy lepiej jest mieć dobry system logowania niż debugger. Z racji tego, że nie mogę teraz używać debuggera muszę, wszystko opędzić logami i naprawdę da się to zrobić. Nie tęsknię również jakoś specjalnie ze możliwością debugowania.
  • #36
    Freddie Chopin
    MCUs specialist
    grko wrote:
    No jeden log również by załatwił sprawę. Naprawdę, niekiedy lepiej jest mieć dobry system logowania niż debugger. Z racji tego, że nie mogę teraz używać debuggera muszę, wszystko opędzić logami i naprawdę da się to zrobić. Nie tęsknię również jakoś specjalnie ze możliwością debugowania.

    Log czego? Że nie wchodzi do pętli w której były tylko jakieś obliczenia? Zresztą myślę że mieszamy sprawy. Gdzie miałbym sobie to zalogować na "małym" urządzeniu opartym na mikrokontrolerze, w którym nie ma systemu plików i 10 GB niepotrzebnego miejsca na karcie pamięci? Albo gdzie mam to wyświetlić, jeśli projektant płytki nie przewidział możliwości dopięcia sobie gdzieś konsoli, bo brakowało mu pinów? "Dziś" na płytkach z mikrokontrolerem ARM debugger jest wyprowadzony praktycznie zawsze, bo przecież jakoś te płytki trzeba zaprogramować, a bawienie się wbudowanymi bootloaderami jest mniej uniwersalne. Przy okazji piny od debuggera rzadko mają jakąś istotną funkcję dodatkową (w końcu producenci mikrokontrolerów też myślą), w przeciwieństwie do pinów na których jest dostępny bootloader. Z mojego punktu widzenia debugger jest dostępny zawsze, w przeciwieństwie do konsoli/UARTa (nie zawsze) czy dużych pojemności na logowanie danych (bardzo rzadko).
  • #37
    tmf
    Moderator of Microcontroller designs
    Ja z kolei myślę, że debugowanie vs. logowanie to nie dwie wykluczające się metody, lecz uzupełniające. Logowanie jest ok, ale jak pisał kol. @Freddie Chopin trzeba mieć gdzie te logi wysyłać, no i druga kwestia -trzeba umieścić w programie fragmenty kodu, odpowiedzialne za generowanie tych logów. Gdyby @Freddie Chopin spodziewał się, gdzie jest błąd, to by go usunął i żadne logi/debugger by nie były potrzebne. Z kolei przy ogólnym sprawdzeniu jak działa program, jakie generuje rezultaty, czy jak wygląda przetwarzanie dużych zestawów danych z pewnością logi są wygodniejsze. Niemniej, jak już wykryję, że jest błąd, to teraz jego dokładna lokalizacja może być łatwiejsza do znalezienia za pomocą debuggera. Ale jeśłi komuś wygodniej jest używać innej metody, to czemu nie. Wolę mieć do dyspozycji kilka metod, niż być zmuszonym do korzystania z jednej.
  • #38
    grko
    Level 33  
    tmf wrote:
    Ja z kolei myślę, że debugowanie vs. logowanie to nie dwie wykluczające się metody, lecz uzupełniające.


    Nigdzie nie napisałem, że się wykluczają. Napisałem tylko, że bardziej sobie cenię logowanie + prostą konsolę od debugera oraz że błąd o którym pisał FCh rówie szybko wychwyciłbym na logach. Zresztą tego typu rzeczy to statyczna analiza kodu załatwia. Warto z niej czasem skorzystać. Poza tym ja mam takie doświadczenia, że bardzo rzadko mam dostęp debuggera (urządzenie z pola, które ma tylko serial port, CAN). Zresztą popatrzcie sobie na jądro linuxa. Może przykład od czapy ale jeśli chodzi o skalę to przebija wszystkie nasze projekty razem wzięte i całe debugowanie opiera się na logach.
  • #39
    trol.six
    Level 31  
    tplewa wrote:
    @trol.six

    Ja ci powiem tak nie da się odpowiedzieć na te pytania... to jak byś chciał odpowiedzieć na pytanie czy samochód jest potrzebny

    Czy samochód jest potrzebny czy nie, w konkretnych przypadkach da się uzasadnić. Np. masz transport w dwie lokalizacje, do jednej jest droga ,a druga znajduje się na wyspie a dźwiganie towaru zajmie dużo czasu. I o takie przypadki pytam :)

    Tak samo jest z debugerem. Masz błąd... dziwne nie jest. I teraz trzeba go znaleźć. Skoro ktoś używa debugera a nie potrafi mi odpowiedzieć jak się tych błędów fantastycznie szybko szuka za pomocą debugera, to może ich nie szuka w ten sposób.

    Nikt nie pisze używam debugera bo lubię. Zwolennicy debugera uważają że przyspiesza programowanie i wręcz jest niezbędny. A ja sobie tego wyobrazić nie potrafie. Pewnie moje programy mają bład na błędzie i działaja tylko dlatego że hakerzy co mi się włamali na kompa poprawiają mi je podczas kompilacji. ;)

    tmf wrote:
    Przechodzę na asembler, widzę, że instrukcja FPU ma prawidłowe argumenty, ale daje nieprawidłowy wynik. Wniosek?

    Każdą bardziej zaawansowaną funkcje testuje, takie błędy wychodzą na pierwszym teście.
    Banalnych nie testuje, bo błąd wychodzi natychmiast. Chcesz mi powiedzieć że nie testujesz swojego kodu?


    tmf wrote:
    No widzisz, czyli zamiast zastosować proste rozwiązanie, wymyślasz jakieś kosmiczne obejście. Czy prościej jest sobie zrobić breakpointa i podglądnąć wartość zmiennej, czy napisać specjalny program testowy?


    Nie jest prościej, bo jak pisałem zmiennych jest powiedzmy 16, program wykonuje ok 10000 iteracji, i nie wiesz kiedy wystąpi ci błąd.
    Ile czasu zajmie ci sprawdzenie 10000 iteracji 16 zmiennych gdzie każda jest złożona obliczeniowo, są właściwe? Jeśli dasz rade w 3 dni to jestem pełen podziwu dla twoich umiejętności szybkiego czytania linijek i obliczenia w locie. Mi by to zajęło ze trzy miesiące. Skąd pewność że podczas analizy nie zrobisz kolejnego błędu? I stracisz kolejne 3 miesiące? Test jest na 99.999% wiarygodny.

    tmf wrote:
    Tu nie wiem, czy piszesz to na poważnie? Co mi da wygrepowanie miejsc w których jest ten kod? Gdyby zapis |= był zawsze zły to ok, ale tu oba mogą być poprawne więc wymaga to większej analizy. W większym programie takie wyszukiwanie zwróci mi od kilkuset do kilku tysięcy linii kodu, więc to kompletnie nic nie daje.

    Jeśli oba są poprawne to nie ma błędu :) Więc czego chcesz szukać? Jak pisałem tam gdzie masz odwołania pisze makra lub funkcje, i już masz gwarancje że jeśli zrobiłeś błąd to jest on w jednym miejscu, wykrywasz go automatycznie. Jak masz multum odwołań typu
    Quote:
    PORT=costam;
    PORT|=costam;

    w kodzie to masz bajzel. To jest to co pisałem, debuger oducza dobrych praktyk pisania kodu.
    .
  • #40
    tplewa
    Level 38  
    trol.six wrote:

    Czy samochód jest potrzebny czy nie, w konkretnych przypadkach da się uzasadnić. Np. masz transport w dwie lokalizacje, do jednej jest droga ,a druga znajduje się na wyspie a dźwiganie towaru zajmie dużo czasu. I o takie przypadki pytam :)


    Widzisz sam sobie odpowiedziałeś na pytanie... są przypadki w których warto coś mieć np. samochód aby nie dźwigać. To samo jest z debugerem można się bez niego obejść tak jak się robiło to kiedyś, ale czasami ułatwia życie.

    Po prostu nie da się tego zamknąć w jakieś tam sztywne ramki i powiedzieć tak czy nie. Wszystko jest bardzo względne. Czasami bez debugera możesz mieć spory problem aby znaleźć błąd.

    Podam ci przykład... z życia wzięty jest sobie STM32F4... soft wywala się powiedzmy raz w miesiącu (nieraz częściej - loteria)... a po wywaleniu masz coś takiego:

    Code:

    CFSR = 0x400
    HFSR = 0x40000000
    DFSR = 0x1
    AFSR = 0x0
    MMAR = 0xe000ed34
    BFAR = 0xe000ed38


    czyli takie fajne IMPRECISERR.... znajdź błąd... ustawiasz sobie ACTLR->DISDEFWBUF i odpalasz na kolejny miesiąc (może dłużej)...

    Więc jak widać wszystko jest względne błędy są różne i nie zawsze pięknie widoczne w kodzie...
  • #41
    User removed account
    User removed account  
  • #42
    Freddie Chopin
    MCUs specialist
    trol.six wrote:
    Tak samo jest z debugerem. Masz błąd... dziwne nie jest. I teraz trzeba go znaleźć. Skoro ktoś używa debugera a nie potrafi mi odpowiedzieć jak się tych błędów fantastycznie szybko szuka za pomocą debugera, to może ich nie szuka w ten sposób.

    No ale czego Ty oczekujesz? Debugger to tylko narzędzie - jak wiertarka, młotek czy scyzoryk. Nie ma magicznej funkcji "znajdź wszystkie błędy", którą wystarczy uruchomić, pójść na kawę i po powrocie dostajesz info gdzie, kiedy, dlaczego, a to wszystko w formie ładnego i kolorowego dokumentu. Już 100x w tym temacie pewnie dostałeś odpowiedź, że debugger jest tylko narzędziem, jak wkrętarka. Można żyć bez wkrętarki, można żyć bez debuggera, ludzie miliony lat już przeżyli bez jednego i drugiego. Nikt również nie poda Ci opisu sytuacji, w której wkrętarka jest absolutnie niezbędna do zrobienia czegoś, ale chyba nie będziesz się spierał, że wkrętarką się szybciej i wygodniej wkręca śrubki niż śrubokrętem. Z debuggerem jest naprawdę to samo - masz narzędzie, dzięki któremu możesz podejrzeć wszystko w danym układzie, beż żadnego specjalnego kodu czy dodatkowych połączeń. Jak tego użyjesz (i czy użyjesz w ogóle) - Twoja sprawa.

    trol.six wrote:
    Każdą bardziej zaawansowaną funkcje testuje, takie błędy wychodzą na pierwszym teście.

    Widzę sami specjaliści. Wiesz dlaczego bardzo wątpię w tego typu przechwałki? Bo ja też testuję kod, szczególnie taki bardziej zakręcony, którego częścią były owe obliczenia. I zgadnij co? Takie błędy nie wyszły na pierwszym teście. Nie wyszły przez dobre kilka miesięcy (a nie tylko ja to testowałem), ponieważ tak się ciekawe składa, że błąd uwidacznia się tylko dla bardzo specyficznych zestawów danych, a w każdym innym przypadku jest ok. Biorąc pod uwagę, że kod o którym jest mowa dostawał jako argumenty dwa floaty, rozumiem że przetestowałbyś ten kod dla wszystkich 1,844674407×10¹⁹ kombinacji, no nie?

    trol.six wrote:
    A ja sobie tego wyobrazić nie potrafie.

    No i co w tym jest dziwnego? Ja nie mogę sobie wyobrazić jak jest tam gdzie mieszkasz, bo nigdy tam nie byłem. Nie wyciągam jednak z tego pochopnych wniosków.

    trol.six wrote:
    Nie jest prościej, bo jak pisałem zmiennych jest powiedzmy 16, program wykonuje ok 10000 iteracji, i nie wiesz kiedy wystąpi ci błąd.
    Ile czasu zajmie ci sprawdzenie 10000 iteracji 16 zmiennych gdzie każda jest złożona obliczeniowo, są właściwe?

    Trzeba było napisać, że zmiennych jest 1000 a program wykonuje trylion iteracji, złożonych obliczeniowo. Byłoby bardziej imponująco. W rzeczywistości w programie bardzo łatwo zidentyfikować kilka punktów kontrolnych, w których zmienne powinny mieć jakąś z grubsza oczekiwaną wartość i sobie to sprawdzić. Następnie jest taki magiczny sposób szukania problemów jak "bisekcja", która sprawia, że te Twoje imponujące 10000 iteracji to maksymalnie 13-14 kroków.

    Problemem chyba jest to, że Ty założyłeś, że debugger to jest Święty Graal programowania, mając go nie trzeba o niczym myśleć, problemy znajdują się same (a jest ich w ogóle mniej, bo boją się debuggera, wiec nie podchodzą), żadnych testów nie trzeba robić, wszelkie formy logowania są wtedy wykluczone, a wyświetlanie sobie zmiennych po UARTcie sprawia, że debugger przestaje działać, wiec się tego nie robi. Tymczasem to po prostu kolejne narzędzie - podkreślam, że kolejne, wiec nie zastepuje wszystkiego innego, tylko uzupełnia. Jeszcze bym zrozumiał tą debatę, gdyby sprawa wyglądała tak, że np. programator kosztuje 10 zł, a debugger minimum 1000 zł. Tyle że dziś programator i debugger to w zasadzie jedno i to samo urządzenie, a nawet jeśli nie, to cenowo różnica jest albo żadna, albo nieistotna. Finalnie zaś chciałbym dodać, że "printf-owanie" zmiennych, zapalanie diody w przerwaniu żeby sprawdzić czy się wykonuje, itd. to JEST debuggowanie (tyle że bez użycia debuggera), a jakoś przed tym się nie bronisz.

    trol.six wrote:
    Test jest na 99.999% wiarygodny.

    Grunt to wysoka samoocena
    trol.six wrote:
    six"]To jest to co pisałem, debuger oducza dobrych praktyk pisania kodu.

    Czyli dobrą praktyką pisania kodu jest chowanie jednolinijkowego przypisania/modyfikacji za funkcją/makrem? Wg której konwencji? Nie rób globalnych zasad ze swoich własnych preferencji, ja np. jak widzę tysiąc makr to mnie od razu coś strzela.

    BTW to nick chyba zobowiązuje, bo ten wątek to już typowy trolling - autor po prostu wszystko testuje tak dobrze, że nie popełnia błędów, a nawet jak się jakiś zdarzy, to wklepie w konsolę magiczną kombinację `grep | egrep | awk | sed | cat /dev/urandom` i błąd od razu się znajduje.
  • #43
    tplewa
    Level 38  
    z3planety wrote:

    @tplewa Nawet mając już tę informację - po co grzebać patykiem na stosie - jak wygodniej jest do tego zmusić komputer (w końcu po to jest aby ułatwiać życie)

    Czy jest konieczne- absolutnie nie. Ale oszczędza trochę czasu. Czy zawsze wystarcza - oczywiście nie, ale wystarcza w 99% przypadków.


    Hmm kolega chyba nie rozumie tego co napisałem... kto mówi o ręcznym grzebaniu w stosie... podałem tylko przykład problemu jaki nie jest łatwy do wyłapania zwłaszcza że zdarzało się to niezbyt często (o czym wspomniałem np. raz w miesiącu - gdzie urządzenie non stop chodziło). Nie mówiąc o tym że sprzęt był zainstalowany kilka kilometrów od firmy na słupie przy drodze... ale tutaj problem rozwiązuje JTAG z Ethernetem (JLink)
  • #44
    User removed account
    User removed account  
  • #45
    trol.six
    Level 31  
    @Freddie Chopin: nie wiem o co ci chodzi, sam krytykujesz moje rozwiązania pisząc że coś jest kiepskie:
    https://www.elektroda.pl/rtvforum/viewtopic.php?p=17129151#17129151
    Chociaż nie widać potem dyskusji w temacie.

    Więc i ja wyrażam swoją opinie. Nie czuje się specjalistą. Myśle że co najmniej połowa czytających ten wątek ludzi piszących programy, ma lepsze umiejętności w tym zakresie ode mnie. To tyle jeśli chodzi o moją samoocenę.

    Jejku... to 99,999 nie odnosi się do perfekcyjności programu, tylko możliwości znalezienia błędu. Jak mówi prawo Murphiego "w programie zawsze jest jeszcze jeden błąd".

    Tematu by nie było gdyby to zwolennicy debugera nie polecali go wręcz jako niezbędne narzędzie. Szczególnie dla początkujących. Więc jestem ciekawy. Osobiście mam inne doświadczenia i chciałem je porównać i dowiedzieć się czegoś. Być może pewnego dnia założe temat jak debugować arma ;)
  • #46
    tplewa
    Level 38  
    z3planety wrote:
    @tplewa Nie to Kolega nie zrozumiał. Cohodziło mi o to że można bez debugera, można bez jakiś wygodnych pluginów- tylko po co? Aby utrudnić sobie życie? i o to mnie chodziło, a nie o ten przypadek


    Owszem można i się używa.. ale czasem się nie da lub ktoś nie ma możliwości. Podany przykład niech kolega zobaczy ile kosztuje najtańsza wersja takiego JLinka z Ethernetem i ile osób na to stać... nie w każdej firmie nawet kupią programiście...

    Jak już ktoś wspomniał debuger jest fajny bo ułatwia życie, ale tylko ułatwia i nie jest to narzędzie niezbędne. Równie dobrze można by napisać że warto mieć np. J-Trace które w wielu wypadkach jeszcze bardziej ułatwia życie (pytanie ile osób sobie kupi).

    Kolejna sprawa to w pracy zawodowej można trafić do firmy gdzie rozwija się jeszcze stary sprzęt z prockami bez takich możliwości (mamy kilka takich w firmie) i trzeba sobie umieć radzić i w takich wypadkach. Osoba przyzwyczajona do używania debugera może mieć tutaj spory problem (bo nie nauczyła się kombinować - tylko nauczyła się wygody).

    Ja mówię tak jak ma się możliwość warto używać, ale nie uznaję tego za konieczność...
  • #47
    User removed account
    User removed account  
  • #48
    simw
    Level 25  
    Niniejszy spór przypomina mi pewien dotyczący Eclipse.
    Po jednej stronie był użytkownik co się upierał, że w widoku lepiej stosować zakładkę "Problems", a drugi, że MUSI być "Console" i pewnie mogliby się pobić, gdyby stanęli twarzą w twarz.
    Cała śmieszność tego sporu wynika z tego, że bez żadnych cudów można widzieć obie zakładki - po prostej modyfikacji perspektywy.
    Debuger jako narzędzie marnujące czas programisty?

    Ot tak refleksja mnie naszła po tym co tutaj przeczytałem :)
    Edit:
    Osobiście uważam, że warto mieć dostęp do wielu narzędzi. Podstawa to umieć się nimi posługiwać i wybierać w zależności od problemu. Debuggery do STM czasami mnie przerastają, ale staram się z nich korzystać. Trzeba też mieć w "szufladzie" diodę do migania lub analizator stanów, albo przejściówkę UART, a i tak najważniejszym z debuggerów jest urządzenie, które należy oprogramować :)
  • #49
    _lazor_
    Moderator of Designing
    A ja uważam że do pisania kodu nie jest potrzebne IDE i dużo klepie w notepad++ albo w VIM i nie wysuwam tezy że IDE jest nie potrzebne i marnuje czas programisty. A nawet debuguje w konsoli za pomocą gdb tui i sobie chwalę.

    Ewidentnie temat jest żartobliwy, bo nie jestem w stanie uwierzyć by ktoś był aż tak narzędzio-oporny by nie używać funkcjonalności często zintegrowanej z IDE, ale zawsze ciekawie poczytać, jak się nawet w ten sposób pobudzi ludzi do dyskusji (nawet o taki banał).
  • #50
    tmf
    Moderator of Microcontroller designs
    trol.six wrote:
    Jejku... to 99,999 nie odnosi się do perfekcyjności programu, tylko możliwości znalezienia błędu. Jak mówi prawo Murphiego "w programie zawsze jest jeszcze jeden błąd".


    Ale ten szacunek jest wyssany z palca. Załóżmy, że robisz wektory testowe dla funkcji. Jak pisał kol. @Freddie Chopin masz jako wejście dwa floaty. Czyli liczba kombinacji 2^64, niemożliwe do przetestowania. Testujesz więc dla wybranych. I tu jest problem - praktycznie każda funkcja zawiera jakieś rozgałęzienia. Powstaje więc problem, jak wygenerować wektory testowe, aby uwzględniały wszyskie kombinacje rozgałęzień? Można kombinować, myśleć i może wpaść na jakiś genialny pomysł. Można też podejść od drugiej strony - skoro program się wysypuje, to określam sytuację w której to następuje. Następnie myślę jakie muszą być warunki na wejściu, aby taka sytuacja wystąpiła i dla nich sobie spokojnie debugguję funkcję. Nie muszę generować miliardów wektorów, aby znaleźć problem. Oczywiście nie gwarantuje mi to, że funkcja będzie doskonała i nie wystąpią inne błedy. Ale przynajmniej ten jeden zniknie. No i oczywiście to nie jest podejście albo-albo, ale uzupeniające.
    Poza tym mimo wszystko prościej i szybciej jest wstawić brakpointa w kodzie i podglądnąć stan MCU w miejscu programu, w którym stan coś mówi o jego wykonaniu, niż np. wstawić w nie kod logujący stan, skompilować, uploadować do procka, odpalić i cierpliwie czekać aż mi się coś zaloguje.
    Kolejna sprawa - uważasz najwyraźniej, że wększość błędów podczas pisania programu to są jakieś wyrafinowane błedy, których wykrycie wymaga wiedzy niemalże tajemnej. Myślę, że jednak większość błedów, przynajmniej w świeżym kodzie, to głupoty - średnik, niewłaściwy operator, błedna konstrukcja logiczna warunku, itd. Tego typu błędy są max upierdliwe, bo siedząc dłuższy czas nad kodem przestajemy je zauważać. Oczywiście, jeśli są programiści, którzy takich błędów nie popełniają to zapewne wymagają oni innych narzędzi, nie śmiem nawet zgadywać jakich, bo to muszą być ludzie na dużo wyższym poziomie świadomości i przejrzeć ich myśli, to jak przejrzeć plan Boga :)
    trol.six wrote:
    Tematu by nie było gdyby to zwolennicy debugera nie polecali go wręcz jako niezbędne narzędzie. Szczególnie dla początkujących.

    Bo właśnie początkujący odnoszą największe korzyści z takich narzędzi. Gdyż to właśnie na początku popełnia się najgłupsze błedy, których się nie dostrzega. Wystarczy przejrzeć tematy na elektrodzie - większość problemów można rozwiązać szybko za pomocą debuggera, ślęcząc nad kodem niekoniecznie. Prosty przykład:
    Code: c
    Log in, to see the code

    Ciekawe ilu początkujących będzie się głowić dlaczego powyższy kod nigdy nie wywoła funkcji cos_tam_zrób(), a ilu stwierdzi, po analizie wygenerowanego kodu asemblerowego, że wykryli błąd w kompilatorze :)

    Dodano po 9 [minuty]:

    trol.six wrote:
    tmf napisał:
    Tu nie wiem, czy piszesz to na poważnie? Co mi da wygrepowanie miejsc w których jest ten kod? Gdyby zapis |= był zawsze zły to ok, ale tu oba mogą być poprawne więc wymaga to większej analizy. W większym programie takie wyszukiwanie zwróci mi od kilkuset do kilku tysięcy linii kodu, więc to kompletnie nic nie daje.


    Jeśli oba są poprawne to nie ma błędu :) Więc czego chcesz szukać? Jak pisałem tam gdzie masz odwołania pisze makra lub funkcje, i już masz gwarancje że jeśli zrobiłeś błąd to jest on w jednym miejscu, wykrywasz go automatycznie. Jak masz multum odwołań typu

    Cytat:
    PORT=costam;
    PORT|=costam;


    w kodzie to masz bajzel. To jest to co pisałem, debuger oducza dobrych praktyk pisania kodu.


    Oba są poprawne syntaktycznie, niekoniecznie znaczy to, że w konkretnym miejscu programu. I tu jest problem - co ci da grepowanie, jeśli nie wiesz, która konstrukcja w danym miejscu kodu powinna być? A nie wiesz, bo wymaga to pogłębionej analizy.
    A jeśli stosujesz w swoim kodzie makra to raczej o twoim kodzie bym napisał, że nie jest przykładem dobrej praktyki. Poprawnie napisane makro niczego nie gwarantuje. Problem z makrami jest taki, że zawsze można je wywołać w taki sposób, aby coś się poknociło.. I poprawne makro, nagle staje się niezbyt poprawne. Posty przykład (poprawne makro):
    Code: c
    Log in, to see the code


    i teraz wywołaj np. f(x<<2, 6) i co? A to tylko jeden z bardziej oczywistych problemów, więc łatwych do rozwiązania. Niemniej powyższe makro pewnie w 99% kodu nie spowoduje problemów, a tylko z rzadka stanie się coś dziwnego. No ale to zupełnie inna historia i na razie nie mieszajmy jej z tematem o debuggerze (chociaż to właśnie jeden z przykładów, kiedy debugger ułatwi znalezienie błedu).
  • #51
    grko
    Level 33  
    tmf wrote:
    Posty przykład (poprawne makro):
    Code: c
    Log in, to see the code


    i teraz wywołaj np. f(x<<2, 6) i co? A to tylko jeden z bardziej oczywistych problemów, więc łatwych do rozwiązania. Niemniej powyższe makro pewnie w 99% kodu nie spowoduje problemów, a tylko z rzadka stanie się coś dziwnego. No ale to zupełnie inna historia i na razie nie mieszajmy jej z tematem o debuggerze (chociaż to właśnie jeden z przykładów, kiedy debugger ułatwi znalezienie błedu).


    IMO w tym przypadku debugger nie ułatwi znalezienia błędu. Bo niby jak? Nie rozwija przecież makr ani też nie wyjaśni jakim magicznym sposobem f(x<<2, 6) nie jest równe tyle ile powinno.

    Tak samo w przypadku:
    Code: c
    Log in, to see the code


    Taki początkujący będzie sobie krokował ten program i nadal nie wymyśli dlaczego ta funkcja się nie wywołuje. Debugger tutaj raczej nie rozwiaze sprawy. Prędzej już jakaś analiza listingu lub wyłączenie optymalizacji naprowadzi co tu jest nie tak.
  • #52
    tmf
    Moderator of Microcontroller designs
    Nie zgodzę się z tobą. W pierwszym przypadku debugger pokaże, że wynik operacji jest inny niż oczekiwany. Da to więc do myślenia i każdy zrozumie, że coś jest nie tak z wywołaniem tego makra.
    W drugim przypadku debugger pokaże, że linia if(...) nie istnieje w kodzie. To powinno spowodować zastanowienie, dlaczego kompilator ją wyrzucił. Może nie są to idealne przykłady, ale jak dojdziesz do rozwiązania bez debuggera? Nie mówię o analizie kodu, tylko np. stosując logowanie? Możesz sobie logować count i zauważysz, że wynosi ono 0, 1, 2, 3, 4 itd. Co raczej zwiększy dezorientację.
  • #53
    grko
    Level 33  
    tmf wrote:
    Nie mówię o analizie kodu, tylko np. stosując logowanie? Możesz sobie logować count i zauważysz, że wynosi ono 0, 1, 2, 3, 4 itd. Co raczej zwiększy dezorientację.


    Tia, jasne. Log pod tym ifem będzie na 100% pokazywał te wartości... A w pierwszym przykładzie można mieć rozwiązanie w 5 sekund robiąc sobie printf. Choćby na PC. Poza tym to właśnie debugger będzie generował zamieszanie. W pierwszym przypadku ten nieszczęsny If nie zginie z kodu i debugger będzie to dziwnie omijał. Dopiero przejrzenie disasembly pozwala wpaść na to, że tego kodu nie ma w pliku wynikowym. Ale przejrzenie disassembly to sobie można zrobić bez debuggera. Prawda?
  • #54
    _jta_
    Electronics specialist
    To może pytanie, czy debugerem moge zastawiać pułapki na dostęp do zmiennych?

    O ile mnie pamięć nie myli, tak - na procesorach Intel-a od 80386 można ustawić sprzętowo 4 takie pułapki i debuggery z tego korzystają.

    Inna ciekawostka: już pod DOS-em był debugger 'SST', który miał 'supertrace' - wykonywał program krok po kroku i sprawdzał 'warunki' (to było wykonanie kodu, który mu się wpisało), przerywając wykonywanie, gdy odpowiedni warunek był spełniony - ale można było wpisać tylko warunki w postaci instrukcji odwołujących się do rejestrów i pamięci, nie np. do adresu zmiennej, która miała być odczytana przy wykonywaniu instrukcji (trzeba by go wyliczać rozkodowując instrukcję, co już na procesorach 8086/80286 było dość trudne); dość łatwo wpisywało się warunek rozpoznający 'call' (o ile nie był indirect; trudniej na 80386, gdzie mógł mieć prefix), czy 'int' (przerwanie).

    Ale wracając do tematu: widywałem osoby, które zużywały parę godzin na prześledzenie działania programu pod debuggerem w celu znalezienia błędu, który dawało się wyłapać poświęcając czasem kwadrans, czasem pół godziny na przejrzenie ostatnich zmian w kodzie źródłowym. Wychowałem się w czasach, gdy komputerów używało się główne w trybie wsadowym, nie interakcyjnym, i co najwyżej można było dostać wydruk (zrzut pamięci, zdekodowane instrukcje) po wystąpieniu błędu - więc się nauczyłem patrzeć na kody źródłowe...

    Do przykładu z #34 nadawałby się debugger z przerwaniami - był taki i pod DOS-em, ten sam, co miał 'supertrace' - wystarczyło puścić program (go), potem Ctrl-Enter i by pokazał instrukcję, na której program się zapętlał. Ale to samo załatwi napisanie programiku, który podłączy się pod jakieś przerwanie zegarowe i zapisze gdzieś adres aktualnie wykonywanej instrukcji - może tak, żeby ten zapis "przeżył" reset, jeśli to zapętlenie powoduje utratę komunikacji z procesorem.

    I myślę, że debugger ma małe szanse pomóc w znalezieniu błędu występującego przy kooperacji działań wielu procesorów - działanie każdego z osobna wygląda poprawnie, ale błąd tkwi w uzgadnianiu między nimi, który kiedy ma co robić, i np. zdarza się, że dwa naraz próbują coś wpisać do tej samej zmiennej, i jest kwestią przypadku, którego wpis pozostanie.

    Dużo będzie zależeć od podejścia programisty: jeśli ktoś uważa debugger za uniwersalny sposób na wyszukiwanie błędów, to zmarnuje mnóstwo czasu; jeśli ktoś trzeźwo pomyśli, czy akurat debugger jest odpowiedni do jego problemu, może skorzystać na używaniu debuggera.
  • #55
    trol.six
    Level 31  
    z3planety wrote:
    W pierwszym swoim poście napisałem - przymusu nie ma.

    I tyle w temacie. Jak nie lubisz i nie widzisz potrzeby to po prostu nie korzystaj.

    A widziałem, widziałem, dziękuje bardzo.

    tmf wrote:
    Piszesz program, który daje dziwne wyniki (niezgodne z oczekiwaniem). Czy prościej jest teraz analizować cały sposób przetwarzania danej zmiennej, czy np. sobie prześledzić jedną instrukcję i zauważyć, że po przemnożeniu wynik jest inny niż spodziewany? Przechodzę na asembler, widzę, że instrukcja FPU ma prawidłowe argumenty, ale daje nieprawidłowy wynik. Wniosek?


    Freddie Chopin wrote:
    Nie wyszły przez dobre kilka miesięcy (a nie tylko ja to testowałem), ponieważ tak się ciekawe składa, że błąd uwidacznia się tylko dla bardzo specyficznych zestawów danych, a w każdym innym przypadku jest ok. Biorąc pod uwagę, że kod o którym jest mowa dostawał jako argumenty dwa floaty, rozumiem że przetestowałbyś ten kod dla wszystkich 1,844674407×10¹⁹ kombinacji, no nie?


    Ciekawe, że niektórzy wiedzą od razu że mają złe dane, a inni nie wiedzą co napisać w programie testowym. Bo jest coś 1,8E19 możliwości.

    Jak taki sporadyczny błąd znajduje się podczas zabawy z debugerem?

    Jak się debuguje programy gdzie masz zależności czasowe? Czy nie wpływa to na ich zmiane?


    tmf wrote:
    Ale ten szacunek jest wyssany z palca. Załóżmy, że robisz wektory testowe dla funkcji. Jak pisał kol. @Freddie Chopin masz jako wejście dwa floaty. Czyli liczba kombinacji 2^64, niemożliwe do przetestowania...

    Być może jest przeszacowany, bliżej byłoby 99,9%. Ale ile błędów w swoich programach nie znajdujesz? Chyba nie powiesz mi że co drugi błąd znajdujesz (50%). A drugie 50% wychodzi w następnych 4 miesiącach. Choć jeśli robisz dwa błędy na jeden projekt, to tak by mogłoby być.

    tmf wrote:
    Można też podejść od drugiej strony - skoro program się wysypuje, to określam sytuację w której to następuje. Następnie myślę jakie muszą być warunki na wejściu, aby taka sytuacja wystąpiła i dla nich sobie spokojnie debugguję funkcję. Nie muszę generować miliardów wektorów, aby znaleźć problem.

    Tak jak pisałem. Zwolennicy debugera "kliknom" sobie pare razy w zmienne i już. :) Ja raczej bez zestawu danych to sobie moge iść na piwo.

    tmf wrote:
    Myślę, że jednak większość błedów, przynajmniej w świeżym kodzie, to głupoty - średnik, niewłaściwy operator, błedna konstrukcja logiczna warunku, itd.

    Pomaga w tym dobry edytor z formatowaniem, plus czytelna czcionka. Przejrzysty styl, co jest imho kluczem do sukcesu ale nie jest łatwe jeśli mamy złożony program. Ja nie zapisuje swoich błędów, czego troszkę żałuje, w sumie chętnie bym się bardziej precyzyjniej podsumował, bo dzięki temu błędów w przyszłości mniej.


    tmf wrote:
    Prosty przykład: /../
    A jeśli stosujesz w swoim kodzie makra to raczej o twoim kodzie bym napisał, że nie jest przykładem dobrej praktyki. /.../
    i teraz wywołaj np. f(x<<2, 6) i co?

    Ano nic. Napisałeś zły kod z makrem, napisałeś też zły kod w C. A więc, ani jednego ani drugiego nie należałoby stosować bo grozi błędem. Niech żyje BASCOM, nie ma tam makr ani volatile, ale jak za dużo napiszemy to się nie skompiluje bo mamy wersje free. ;)

    Dodam że w kodzie który wrzuciłeś nie ma też sei(); Ale skoro makra są złe, to pewnie masz własną implementacje. ;) Być może ukrywa się w funkcji. ;)

    Poza tym napisałem o makrach i funkcjach. A nie że makra są lepsze od funkcji, bo przeważnie nie są. Więc odnosisz się do wydumanych argumentów.

    tmf wrote:
    Wystarczy przejrzeć tematy na elektrodzie - większość problemów można rozwiązać szybko za pomocą debuggera, ślęcząc nad kodem niekoniecznie

    Być może tak być może nie :) Może kiedyś przeglądne je pod tym kątem.

    tmf wrote:
    I tu jest problem - co ci da grepowanie, jeśli nie wiesz, która konstrukcja w danym miejscu kodu powinna być? A nie wiesz, bo wymaga to pogłębionej analizy.

    Albo wpis PORT=costam; jest dozwolony albo nie. Jeśli coś takiego widzisz to masz potencjalne źródło błędu.
    Jeśli masz dozwolone warunkowo a nie znasz tych warunków nie jesteś w stanie przewidzieć niczego. Może działać, a może za jakiś czas przestać.

    tmf wrote:
    W drugim przypadku debugger pokaże, że linia if(...) nie istnieje w kodzie.

    grko wrote:
    Dopiero przejrzenie disasembly pozwala wpaść na to, że tego kodu nie ma w pliku wynikowym.

    A czasem coś jest. ;) U mnie jedna iteracja się wykona :) dla opcji -O2 -Os, niemniej jednak przy -03 to już śladu nie ma. Listing:
    Code: avrasm
    Log in, to see the code

    .
  • #56
    User removed account
    User removed account  
  • #57
    Freddie Chopin
    MCUs specialist
    trol.six wrote:
    Ciekawe, że niektórzy wiedzą od razu że mają złe dane, a inni nie wiedzą co napisać w programie testowym. Bo jest coś 1,8E19 możliwości.

    Jak taki sporadyczny błąd znajduje się podczas zabawy z debugerem?

    Naprawdę szukasz dziury w całym i wybitnie nie patrzysz na szerszy obraz. Kod o którym teraz piszesz to nie była jedna funkcja na 5 linijek, tylko jest to część większego kodu mającego obliczać trajektorię silników. Akurat tak się składa, że gdy problem wyszedł to od razu to widać, ponieważ silniki zamiast poruszać się płynnie wykonywały jakieś dziwne ewolucje. W takiej sytuacji błąd jest już powtarzalny, bo wiesz jaki zestaw danych powodował dziwne zachowanie. Programik testowy na PC nic by Ci nie dał, bo - jeśli dokładnie czytałeś - domyślnie na PC w GCC FMA nie jest używane, więc po prostu byś się dowiedział, że na PC wynik jest super, problemu nie ma. Mając powtarzalny problem o widocznym objawie wystarczy te dane zapodać, prześledzić w kodzie co i gdzie się dzieje, w odpowiednim miejscu unieść brew i zakląć pod nosem pytając "wtf?" skoro powinno wyjść zero a nie wychodzi, a następnie zgłębić sprawę bardziej.

    Czy da się znaleźć taki problem bez debuggera? Oczywiście.
    Czy da się taki problem wychwycić w testach jednostkowych odpalanych na PC? Wątpliwe (po pierwsze problem nie występuje zawsze, po drugie wymaga użycia FMA).
    Czy da się taki problem złapać logowaniem? Tak, tyle że co z tego że zalogujesz sobie że otrzymałeś niepoprawny wynik, skoro nie wiadomo skąd się on wziął? Będziesz logował wartość każdej zmiennej po kolei, to - jak widać było z przykładów - problem MAGICZNIE znika (bo kompilator przestaje używać FMA gdy są mu potrzebne wyniki cząstkowe).
    Co z printfowaniem wyników częściowych? Patrz wyżej, problem magicznie znika.

    Nigdzie nie jest napisane, że dowolnego problemu nie da się znaleźć bez debuggera. Jest to narzędzie, które kosztuje grosze i nie zużywa extremalnych ilości prądu, wiec po prostu nie widzę powodu aby go NIE stosować. Być może w wielu sytuacjach jest zbędny, ale te sytuacje gdzie okazuje się bardzo przydatny sprawiają, że i tak warto.

    trol.six wrote:
    Jak się debuguje programy gdzie masz zależności czasowe? Czy nie wpływa to na ich zmiane?

    Mniej niż printfowanie zmiennych i logowanie, więc wiesz... (;
  • #58
    User removed account
    User removed account  
  • #59
    gaskoin
    Level 38  
    Przede wszystkim rozmawiacie o kilku różnych rzeczach, wybierając co jest lepsze. Porównywanie używania debuggera do pisania testów jest nielogiczne. Samych testów też jest kilka rodzajów.

    1. Makro, które napisał @tmf to wręcz idealny kandydat do napisania testu jednostkowego na PC. Jeżeli ktoś ma w programie takie funkcje i wgrywa kod + debuguje żeby je sprawdzić to po prostu marnuje czas. Jeżeli już przy testowaniu coś idzie nie tak, to możesz debugger uruchomić na PC. Nie ma też co przesadzać z pokrywaniem pełnej przestrzeni.

    2. Test silnika opisany przez @Freddie Chopin zgrubnie wartości wyjściowe też mogą być przetestowane testem jednostkowym, ale zwykle lepiej jest testować to testem integracyjnym na urządzeniu. Takie testy też mogą być automatyczne, ale z reguły wymagają więcej wysiłku i złożoności. Jeżeli już przy testowaniu coś idzie nie tak, to możesz debugger uruchomić na docelowym urządzeniu.

    3. Testy integracyjne testują też, czy na docelowym urządzeniu kod zachowa się tak samo jak się zachował podczas testowania na PC.

    4. Są jeszcze inne rodzaje testów, do doczytania na zadanie domowe. Jako przykład podam wydajnościowe.

    5. Generalnie testy nie są dowodem na nieistnienie bugów. Testy przede wszystkim wykrywają, czy jakakolwiek wprowadzona zmiana na drodze kod-budowanie nie spowodowała zmiany zachowania oprogramowania (chyba, że jest celowa).

    6. Debugger jak sama nazwa wskazuje służy do usuwania bugów.

    7. Pierdoły typu:

    Code: c
    Log in, to see the code


    Wykrywa się statyczną analizą kodu + ustawiając flagi kompilatora na dość rygorystyczne (typu warnings as errors), a nie debuggerem. O ile test jednostkowy wcześniej nie wykryje błędu. Przykładem takiej analizy może być @trol.sixowy grep, ale istnieją bardziej cywilizowane narzędzia :)