top | item 1873413

What do you want to see in Learn C The Hard Way?

53 points| alnayyir | 15 years ago | reply

I bought the domain to force myself to do something with the free time I'll soon have an abundance of.

I want to see more young programmers doing systems programming and making cool things with the language that forms the basis of almost everything we use.

What do you want to see covered in a 'book' that purports to teach C the hard way? :)

I will be following Zed's example, although I'll be influenced by my learning under K&R. I really do want to be demonstrating proper, modern C.

120 comments

order
[+] there|15 years ago|reply
whatever you do, make your examples bulletproof. even if it's not how you would normally write the code and it seems overly cautious, do your audience a favor and write the example that way anyway.

if there are any buffer overflows, integer overflows, off-by-one's, signedness issues, failure to check return values of everything, use of typically insecure things like sprintf instead of snprintf, all of these problems will just carry over into your readers' code. please do us all a favor and stress the importance of writing secure code from the ground up and not as an afterthought or something only done just before releasing it.

[+] anigbrowl|15 years ago|reply
Or as a compromise, start with simple, easy-to-read examples teaching basic principles. Give them datasets that will cause the program to blow up, and then explore both the causes and solutions to failure. Ideally, work back from the failures and encourage the reader to try out solutions that don't work so as to develop rigorous problem-solving skills.

I've always felt that teaching 'don't do that, cause it's bad' sticks rather poorly - unless something that obviously dangerous is involved, making your own mistakes is much more educational than memorizing a set of best practices and never even peeking into those blind alleys or pitfalls. You can do that and have good habits, but you'll have a dogmatic rather than a fundamental grasp of the knowledge, and this will constrict further development.

[+] gchpaco|15 years ago|reply
One of the things that I admire most about W. Richard Stevens's books is that he checked the return value of everything, even printfs. Anal, sure, but that's what you're supposed to do in C and when you write demo code that doesn't, even if you surround it with warnings like "DO NOT DO THIS", beginners will still do it. Better to get the habits in right from the start.
[+] misham|15 years ago|reply
I disagree. If I'm learning a new language, I'm too busy worrying about the commas and semi-colons, not whether or not I'm using strcat or strncat. Worrying about overflows, signedness, etc. is something you do once you're more comfortable with the language.

It would be nice to provide links to articles and books on why one should use snprintf instead of sprintf or what is integer overflow and how do you deal with it and other topics for writing secure code.

However, as a beginner, it will simply not register since I'm more worried about having used a period instead of an arrow to access a struct member.

Perhaps, instead of writing a beginner C book, an advanced C book is needed more.

[+] ced|15 years ago|reply
On the other hand, not all C code have to be secure. If I'm building a game for the Wii, don't bother me with stack overflows. The same goes for all the simulations out there (C is used about as much as Fortran in research). That's a lot of code.
[+] alnayyir|15 years ago|reply
I don't think the learner would appreciate the subtleties, and I don't agree that they'll learn anything from it.

I can reinforce each lesson/problem you're describing one by one through the exercises, but a new person simply wouldn't know good code if it slapped them in the face.

Confer with Learn Python the Hard Way to get a feel for the aesthetic and technique I'm working towards.

I don't want to write bulletproof code, I want to teach them how and why to write bulletproof code.

I'm not qualified to meet that kind of lofty standard anyway.

[+] zedshaw|15 years ago|reply
My plan was to make people use valgrind all the time after about lesson 10. Rather than you having to teach them all the various errors, you just let valgrind teach them by telling them their stuff must be valgrind pure.

Other than that, pretty much the same style as I did LPTHW.

Also, read:

http://sheddingbikes.com/posts/1288945508.html

There's more advice there.

[+] alnayyir|15 years ago|reply
I sent an email after reading that post, was inspired to do this because of it. I planned on having them use valgrind as well.
[+] adambyrtek|15 years ago|reply
Make sure you explain pointers well, the additional level of indirection introduced by them is usually hard to grasp for beginners.

Show the relation between pointers and arrays. Offer some best practices on using pointers. Explain the most common caveats like buffer overflows, problems with null terminated strings or off by one errors.

[+] cperciva|15 years ago|reply
Even better, make sure you explain function pointers well.
[+] loup-vaillant|15 years ago|reply
I second the proper teaching of pointers. However, make sure you explain variables just as well, for they too introduce a level of indirection¹, which is almost always overlooked.

C doesn't syntactically distinguish rvalues and lvalues, so this level of indirection often goes unnoticed. I strongly suspect this is why learning pointers is often hard: trying to grasp an additional level of indirection before having comprehended the first one is nearly hopeless.

[1] Variables are containers for values. This is isomorphic to a constant pointer to a mutable cell.

[+] misham|15 years ago|reply
Why not base it on a project? If you want more people to do systems programming (I am assuming kernel and driver development), why not take something from http://kernelnewbies.org/ and turn it into a simple project or write a character driver. People will learn how to write code for the Linux Kernel, learn how to interact with that community and perhaps become more interested in systems development as a result, if that is your goal.

In the context of writing a driver, you will have to cover concurrency, multi-threading, semaphores/mutexes, function pointers (callbacks), memory management, etc.

One personal side note, would be nice if you integrate TTD into the projects. The number of C developers that I deal with who do not understand the concept of a unit test is amazing.

Also, please cover C99 and talk a little about compilers, linkers and assemblers. You can concentrate only on one binary format (doesn't matter which one) as long as you explain a little bit about how your C code gets converted into machine format and what does that mean.

I would ask myself: "What makes my book on C different from all the other ones?"

Why should I spend my time on reading your book instead of any number of other tutorials or K&R?

EDIT:

Forgot to add, please provide a public repository for your code examples and start using something like Git right away. That's one thing I really enjoy from all the Rails books, they push you into using an RCS immediately.

[+] zedshaw|15 years ago|reply
No, I disagree with most of this. A LTHW book covers just enough of the language that someone could then go learn the things you mention from another book. At the end you could lightly cover testing, but most people can barely get an editor installed. No way they can learn multi-threading, TDD, an entire project, and an RCS.

It'd also dilute the focus of the book.

[+] alnayyir|15 years ago|reply
>Why not base it on a project?

There might be a project. I'm modeling it after Zed's approach to some degree regardless.

>(I am assuming kernel and driver development)

Not particularly.

>turn it into a simple project or write a character driver

Nah.

>People will learn how to write code for the Linux Kernel

That is in fact, the opposite of what I'm trying to do.

I want to teach C, not Linux.

>would be nice if you integrate TTD into the projects

I'll demonstrate how/why, it won't be an integral part of it. TTD is use-case specific, not a universal benefit.

>The number of C developers that I deal with who do not understand the concept of a unit test is amazing.

That's a cultural problem, not a pedagogical one.

>Also, please cover C99 and talk a little about compilers, linkers and assemblers.

I'm going to aim for implementation agnostic insofar as it's possible while keeping them aware of the caveats.

What you're advocating is a significant departure from Zed's example. Not my goal.

>explain a little bit about how your C code gets converted into machine format

Implementation specific, outside scope.

>"What makes my book on C different from all the other ones?"

Out of scope of what I'm worrying about, it's a book, not a startup.

>Why should I spend my time on reading your book instead of any number of other tutorials or K&R?

Pretty sure you're not the crowd I'm aiming for, but I'll be happy if you can glean value from it.

Most C books are provincial or overly prosaic. I'm not interested in explaining, I'm interested in whipping people into coders. They can get their compiler and language implementation from a Comp Sci program.

[+] malandrew|15 years ago|reply
I think it would be cool to see any of the following:

Learn Haskell the Hard Way

Learn Erlang the Hard Way

Learn Common Lisp the Hard Way

Learn R the Hard Way

Besides a "Learn X the Hard Way", I would actually like to see more people try to recreate the style of "The Little Scheme", which uses the socratic method to teach the learner. I think the socratic method requires the user to rack their brain a bit more, but results in much greater enjoyment and retention.

I would much prefer to see these two:

"The Little Haskeller"

"The Little Erlanger"

For example, it would be brilliant if someone can explain monads and list comprehension with the same eloquence as The Little Schemer explains currying and YCombinator.

[+] jimwise|15 years ago|reply
There _is_ a Little MLer (with examples in Caml and Standard ML), which teaches type-based programming very well, and would be worth reading for anyone setting out to learn Haskell, I imagine (I respect Haskell's purity, but program in ML and Scala, the same way I respect Ada's safety, but program in C, so a better Haskeller than myself may disagree. :-)).

However, none of the Little ___er books are, of themselves, good ways to learn to use the language they are in; they're more like finger exercises when learning piano -- they reinforce your mental muscles to make thinking in the right way for those languages feel more natural.

[+] alnayyir|15 years ago|reply
I picked C because I want people to learn C specifically to build the kinds of things C is good for these days. This isn't completionism, it's very purposeful

I'd like to see the little Erlanger too actually.

[+] redstripe|15 years ago|reply
Reading through Zed's tutorial reminded me of some Pascal and C tutorials I downloaded in the old BBS days. They were a great introduction to both languages when I was just learning to program.

I just had a look on simtel but I couldn't find them. Maybe you should put some effort into scanning old software archives and seeing if you can unearth them. C is pretty old - you wouldn't be the first one that had this idea.

[+] alnayyir|15 years ago|reply
I'll be referencing a lot of material, not all of them programming related. I'll try to dig up some old text files I liked as a kid per your recommendation.
[+] Jabbles|15 years ago|reply
I think your goal will be more easily and better achieved by writing a "So You Found Python Easy?" book. C is not (IMO) a good language to teach people that are just starting to program.

However, if you wish to try anyway, I recommend looking at "Assembly Language Step-by-Step: Programming with Linux" by Jeff Duntemann. It aims to teach people assembly language as their first language, so you may find it useful.

[+] alnayyir|15 years ago|reply
I'm doing this book precisely because programmers who already know a language aren't ever getting around to learning systems programming or how things work.
[+] Tichy|15 years ago|reply
I understood K&R years ago, but somehow I feel completely inadequate to being a C programmer. I think there is some kind of black art involved in memory management. I checked recently and it seems K&R doesn't even talk much about memory management.

I just wish to learn the current state of the art - what are best practices that have evolved since K&R?

[+] silentbicycle|15 years ago|reply
There's a chapter on memory management* in Hanson's _C Interfaces and Implementations_ (http://sites.google.com/site/cinterfacesimplementations/), which is one of the better advanced C books I've read.

* Mostly, arena-based allocators.

Paul Wilson's "Uniprocessor Garbage Collection Techniques" (http://citeseerx.ist.psu.edu/viewdoc/summary?doi=10.1.1.47.2...) is an excellent overview, as is Jones and Lins's _Garbage Collection: Algorithms for Automatic Dynamic Memory Management_.

[+] alnayyir|15 years ago|reply
That feeling of inadequacy and incompleteness post-K&R is something I experienced too and is something I'm hoping to address.
[+] Teckla|15 years ago|reply
One important thing I would like to see in such a book is one or more chapters devoted to memory management best practices.
[+] alnayyir|15 years ago|reply
100% agreed, I see way too many people struggling with realloc/calloc in ##C, let along comprehending heap fragmentation.
[+] jswinghammer|15 years ago|reply
Honestly the closer you stay to the spirit of K&R the better the site would be. I've looked at a lot of C books over the years and K&R is the only one I thought was even decent.
[+] alnayyir|15 years ago|reply
I'm not trying to replace K&R, but I'll be inspired by it since I grew up with it.
[+] sleepdev|15 years ago|reply
I am not sure how applicable it is to an introductory text, but I would be interested in learning more about the internals of compilation and linking. What is the minimal necessary amount of work that needs to be done to interact with existing C libraries (header files, ELF format, and how that all fits together).
[+] alnayyir|15 years ago|reply
Rather avoid imp specific like ELF.

I'll encourage reusing existing code/libraries.

[+] mprny|15 years ago|reply
The memory model. Explain why given: int a[100] and char* p = a, a and p point to the same place but a + 1 and p + 1 do not. C's memory model is easy in concept, one huge array of memory cells. But in practice it can be a rats nest of pointer arithmetic.
[+] dfox|15 years ago|reply
What I really miss is some C book that teaches the modern approach to "object-oriented" C (as done in Gtk, Apache, CPython etc.). Actually many programmers (presumably with only passing knowledge of C programming) even actively proclaim that you cannot program in C in this style.
[+] dfox|15 years ago|reply
And what comes almost directly from this is using (and writing) libraries and not programming everything yourself from scratch. NIH syndrome is particularly strong in many C programmers.
[+] alnayyir|15 years ago|reply
I'll teach function pointers, and might expose them to some style of OO C, but I haven't made any decisions on it.

My approach is going to be relatively unflavored by the Macro Hell of other projects. I'd rather not instill those habits. They can learn that on their own time.

I want the learner prepared to write clean sysprog code. That's it, the rest they can learn having been taught proper C and make their own stylistic decisions.

[+] amalcon|15 years ago|reply
Just because you're working in C doesn't mean you need to handle every detail yourself. In fact, please don't handle every detail yourself. Show your readers how to use some of the great libraries C has to offer. Not just system-level abstraction layers, either.

You need to go get libraries for a lot of the stuff you'd normally use the standard library for in a more modern language. These libraries exist, and many of them are excellent, but because they're not built-in, people are less likely to use them. This is especially dangerous in C, because it requires so much work to do anything even vaguely complex.

edit: That came off as saying "Teach some libraries". What I really mean is "Teach people to go find libraries."

[+] ronnieCA|15 years ago|reply
I don't know if this is outside of the scope of your plans, but threading issues are a big one that jump out for me. POSIX threads can cause all kinds of wonderful headaches, it would be nice to see some solid advice on the does and dont's.
[+] alnayyir|15 years ago|reply
I plan to follow Zed's model for 52 exercises, I don't see any reason why I shouldn't cover multi-threading and a perhaps a few different concurrency models in the latter half.
[+] crux_|15 years ago|reply
I'm not sure it makes sense any more to teach C to beginners -- by the time someone has a need to write C code, they really ought to have mastered programming in another language or three, first.

Personally, I think a teaching/review ladder would be as or more helpful than a tutorial text. Getting good at C, at least from my current starting point, seems to mostly be a matter of discipline and practice.

I'm thinking of something like this: http://gtl.xmp.net/

Along those lines ;) I'll probably be releasing code from my first medium-sized C project in a week or so... anyone care to offer tips on how to get more experienced eyeballs on it?

[+] alnayyir|15 years ago|reply
>I'm not sure it makes sense any more to teach C to beginners

Good thing I'm not writing it for beginners.

>I'll probably be releasing code from my first medium-sized C project in a week or so... anyone care to offer tips on how to get more experienced eyeballs on it?

Uh, that's a toughie actually. IRC can be pretty rough.

[+] wyclif|15 years ago|reply
Other than K&R (which everyone knows about), what is the current CW on best C books?
[+] alnayyir|15 years ago|reply
You usually have to get pretty implementation/purpose specific beyond that. More often than not, the next step is APUE, which is dissatisfactory for what I have in mind.
[+] checker659|15 years ago|reply
Just one request: Would you be able to release individual chapters as you are done with them instead of waiting to finish the whole book? Thanks!
[+] alnayyir|15 years ago|reply
Plan on it, I'll be working on a tight feedback loop since I'm not even remotely qualified enough to be doing this.
[+] callahad|15 years ago|reply
I'll go ahead and pledge that if you write it, I will buy a copy. I love LPTHW's emphasis on exercises. It's one thing to read and understand a concept as presented. It's another thing entirely to actually apply it to problem.