On the Virtues of Assembler

Matthew

I left the private sector in a large part because I was sick of writing code, it is ironic, although in hindsight, not surprising, that I am still surrounded by it. This situation has turned me mildly retrospective, and I’ve been trying to figure out when it was I finally got, I mean really, natively, understood pointers.

I’m a firm believer that the ability to play with pointers is a talent, not a skill. I don’t think it can be taught. Sure, you can lecture on it, and I can get you to pass any multiple choice, fill in the blank, “knowledge of pointers” test, but I’ve found, and smarter people agree, that less than half of all people are able to juggle pointer abstraction in their head. I did most of my early programming in high level languages, and never really had to deal with pointers. I understood them, but it took a few seconds on every line of code to dissect it and make sure I was using them correctly.

I realized last week that I get it. Totally. And I blame Assembler.

If you were taught Assembler well, alongside a decent CPU structure course, Assembler is all about pointers. You just don’t call them that. You’ll learn about addressing, memory locations, address registers and the Program Counter, and you’ll figure it out, because you have to figure it out, you can’t abstract them away, and at the end of it, without realizing it, you’ll have mastered pointers. Even the literals you use are contained in an instruction in a memory location pointed to by the Program Counter. Everything in Assembler is a pointer.

A lot of my peers don’t understand why I tell them, if they’re only taking a few programming courses, to take the lowest-level languages possible. This is the reason. The closer you are to the silicon, the more real examples you’ll get about why you’re told to do things a certain way. Don’t understand what’s so bad about strings? Parse one in assembler. You’ll never forget it. Why can’t you assume a flat address space? Address more than 256 bytes with an 8-bit processor in assembler, and you’ll be intimately familiar with paging and banking. Very soon you’ll realize the elegance of arrays, that they’re not just native to your language (unless you’re unlucky enough that they’re objects instead), they’re native to your processor, and the inner loop of

while(*s++ = *t++);

is probably a single CPU instruction[1].

I love assembler. I get a rush when I can imagine exactly how the MCU is tossing bits around with every instruction. It’s weird, I know, but if you’re programming in any real capacity, you should love it to.

[1] On the 68k, it (should be) compiled to something like:

strcpy:
  MOVE.b  (A1)+, (A2)+  ; 14D9
  CMPI.b  #0,(A1)       ; 0C11 0000
  BNE     strcpy        ; 66F8

2 Responses to “On the Virtues of Assembler”

  • Leah Shanker Says:

    I completely agree with you: it wasn’t until I took CS200 (Assembly & Architecture) where I felt I could *actually* speak to a computer. It even made me a better high-level programmer! When you have to manage the stack manually, it’s so true that you’ll never forget it.

    But even now that I really understand pointer arithmetic, I still really hate it and think it should be abstracted away :)  

  • Kenji Yamamoto Says:

    I couldn’t agree more, pointers and assembler go hand in hand. Pointers are extremely valuable, especially if you are doing low level hardware or embedded code where you can’t handle the overhead of pushing data structures to the stack.

Leave a Reply