you need to stop using print debugging (do THIS instead)

405,390
0
Published 2022-10-01
Adding print statements to debug your crashing program is a tale as old as time. It gets the job done... most of the time. As your code gets more complex and larger, print debugging quickly becomes unfeasible.

Using gdb and core files, you can easily cut your debugging time down. In this video, I'll be discussing a pet program that I wrote and using a core file to debug an issue with our program. We'll talk about how to get your program and kernel to produce a core file on segmentation fault, as well as a few techniques to debug C and C++.

🏫 COURSES 🏫 Learn to code in C at lowlevel.academy/
đź“° NEWSLETTER đź“° Sign up for our newsletter at mailchi.mp/lowlevel/the-low-down

🔥🔥🔥 SOCIALS 🔥🔥🔥
Low Level Merch!: www.linktr.ee/lowlevellearning
Follow me on Twitter: twitter.com/LowLevelTweets
Follow me on Twitch: twitch.tv/lowlevellearning
Join me on Discord!: discord.gg/gZhRXDdBYY

All Comments (21)
  • For anyone who doesn’t know, in the older references, core meant memory, so when the core is dumped is actually writing the current state of memory into a file
  • @maximkulkin2351
    Print debugging still is the most universal way of debugging. You can do it local, you can do it remote you can do it in embedded, you can do it in a high volume processing code that would be just time consuming to step through (or when you don't know exactly where the problem is and can't put conditional breakpoints). Core files can only help with memory problems (when your code crashes), but won't help when it doesn't crash, but just produces wrong resutls.
  • @glowiak3430
    6:13 Fun fact, this is a mistake. As this array's length is 100, its maximum value is 99, so entering 100 will cause a crash anyway.
  • @dfs-comedy
    Core files and debuggers are indeed very useful. But honestly... the occasional debugging printf() is perfectly fine too. I've caught a lot of bugs that way without having to fire up a debugger.
  • @icankickflipok
    This man is the perfect programming YouTuber for me. I’ve noticed lately at my uni in my courses that all the other students complain at an assignment/task that needs to be done in C (we’re in Operating Systems and we just wrote the first part of a shell where we had to create and implement the cd, pwd, and exit commands, now we’re going to exec the other commands as well as their arguments, and the whole class whined out loud when they were told that was the next assignment due next week. He also teased at the possibility of making us write our own memory allocator, which got even more audible rejection from the other students). However, I get excited at the thought of it. I love writing in C, I love the challenges it brings. My professor even pointed it out to me when I went to see him during his office hour to discuss getting an internship, how to go about it, what to prepare for, etc. that I seemed to really enjoy working at a low level close to the hardware. So, as a guy who seemingly loves writing low-level code, finding a programming YouTuber whose channel name is literally “Low Level Learning” is the best thing that I’ve found on YouTube this year so far.
  • Debugging complex systems with time dependent interactions (user input, network connections, video game AI, user interfaces etc) are pretty much impossible with a debugger. The biggest problem here is that the debugger is extremely invasive in terms of time. You hit a break point and it literally freezes your entire application. This is a bit of an issue if you have code that interacts with real time things, which lets face it, is most of the difficult work in software engineering. I do use debuggers where I can and where it's the best tool for the matter at hand. But I am here objecting to the click-bait. Yes, please carry on using logging for debugging, as most debugging of complex systems really requires it.
  • minor correction: "ulimit -c unlimited" means allow a core file be created with unlimited size, not "the kernel is allowed to produce an unlimited amount of core files"
  • @sthex4640
    I like how you said we can look at the assembly instructions to debug this and resigned from doing so as soon as you saw them
  • @abdox86
    Already using gdb on low level stuff, it’s ironic… thanks a lot man I’m really blessed by ur channel.
  • Don't do "typedef unsigned int uint32_t". The size of an int is compiler dependant (although it usually is 32 bits). Include stdint.h if you need exact size integer types.
  • This is very basic debugging for crashes but the video title sounded like more. Print statements to deal with non fatal errors are still quite useful.
  • @anon_y_mousse
    It would also be helpful to demonstrate how to write test cases and how best to separate into multiple modules. Also, you should check the number only once when read in from the user as well as stop using magic numbers. Might also want to demonstrate using `gdb` even if your program isn't crashing.
  • Good video , i just saw a video from Dave Plummer (ex Microsoft software engineer) and i learned to use the f_s functions all the other F functions are not safe, can bus buffer overflow , the new way so use prtinf_s, the video of Dave is called Stupid C tricks , i saw it and he's right , has to do witn functions not taken in account buffer lengts, and not checking them , not adding null remintator and so on, there are new functions and they have in common that they are named as the original functions but added with _s , these are safe functions can not induce a buffer overflow, good explanation also from Dave.
  • @maaznaseer9706
    Or you can gcc -fsanitize=address to see where the segmentation dump core occurred, we use this method alot to understand where the pointer has failed. If not this, valgrind is the second choice of command to understand memory leaks.
  • @ishashka
    When I switched from python and C# to C, one of the problems I had was that there's no stack traces when something goes wrong. But this is actually even more useful than a stack trace. Amazing
  • @system64_MC
    6:04 I think I noticed a small error in the if statement the last index of an array is always the size of the array minus one because arrays starts at 0 (except in LUA). So the maximum index of the array is 99, and not 100. if you select a box with 100 as ID, your program will segfault because index 100 is out of bounds. To fix that, you have to either replace the ">" sign to ">=" sign, or you can do if (i > 99) { ... }.
  • @Boringpenguin
    This is super helpful for beginners as well! Thanks a lot!!
  • @ToyKeeper
    After writing software for 40 years in many languages, from the highest to lowest levels, including patches to some of the software used in this video, here's what I've learned about debugging: 1. The best debugging technique is to just read the code. If the code is too complex to trace in your head, it probably needs to be rewritten anyway. 2. After that, nothing beats print style debugging. It's easy, simple, and works in almost any context. 3. Debuggers and profilers are nice luxuries to have sometimes, but are frequently not feasible.
  • @darius0501
    if i knew this in my first year where i've learned trees and graphs in C imagine all the seg faults thank you for this!
  • @SneezewipeYT
    Woah this is cool! I wish I'd known about this when I still wrote in C back in uni. Great video!