1

How can one recognize the difference between while (1) and do ... while in assembly?

thanks

3
  • 1
    Is the do while statement do { } while(1)? Or is there a different condition than true in the while?
    – JAL
    Nov 17 '16 at 21:22
  • 1
    Different compilers employ different conventions on various optimization levels. I fear there is no 'generic' way.
    – Nordwald
    Nov 18 '16 at 10:12
  • As others have said, it varies between compilers. You can use IDA Pro or another program to decompile, and for things like this they're pretty accurate. I'm honestly not sure if it's in the demo version of IDA. The difference between those two loops is whether the chunk is evaluated first, so if you can isolate the while code you can just see whether it checks a condition before or after executing the body (probably. Optimizations can do very dirty stuff).
    – Lupe
    Nov 19 '16 at 2:58
4

This answer assumes you are trying to compare while (1) with do { } while(1) for simplicity, but should work with other conditions:

Take these two small C programs:

Just while:

#include <stdio.h>
int main(){
   while(1)
      printf("This is a loop\n");
   return 0;
}

and do while:

#include <stdio.h>
int main(){
   do
      printf("This is a loop\n");
   while(1);
}

Using gcc/clang to generate the platform-specific assembly (I'm on an Intel Mac) with gcc -S loop.c, we can see the differences in the calls:

Just while:

    .section    __TEXT,__text,regular,pure_instructions
    .macosx_version_min 10, 11
    .globl  _main
    .align  4, 0x90
_main:                                  ## @main
    .cfi_startproc
## BB#0:
    pushq   %rbp
Ltmp0:
    .cfi_def_cfa_offset 16
Ltmp1:
    .cfi_offset %rbp, -16
    movq    %rsp, %rbp
Ltmp2:
    .cfi_def_cfa_register %rbp
    subq    $16, %rsp
    movl    $0, -4(%rbp)
LBB0_1:                                 ## =>This Inner Loop Header: Depth=1
    leaq    L_.str(%rip), %rdi
    movb    $0, %al
    callq   _printf
    movl    %eax, -8(%rbp)          ## 4-byte Spill
    jmp LBB0_1
    .cfi_endproc

    .section    __TEXT,__cstring,cstring_literals
L_.str:                                 ## @.str
    .asciz  "This is a loop\n"


.subsections_via_symbols

do while:

    .section    __TEXT,__text,regular,pure_instructions
    .macosx_version_min 10, 11
    .globl  _main
    .align  4, 0x90
_main:                                  ## @main
    .cfi_startproc
## BB#0:
    pushq   %rbp
Ltmp0:
    .cfi_def_cfa_offset 16
Ltmp1:
    .cfi_offset %rbp, -16
    movq    %rsp, %rbp
Ltmp2:
    .cfi_def_cfa_register %rbp
    subq    $16, %rsp
    movl    $0, -4(%rbp)
LBB0_1:                                 ## =>This Inner Loop Header: Depth=1
    leaq    L_.str(%rip), %rdi
    movb    $0, %al
    callq   _printf
    movl    %eax, -8(%rbp)          ## 4-byte Spill
## BB#2:                                ##   in Loop: Header=BB0_1 Depth=1
    movb    $1, %al
    testb   $1, %al
    jne LBB0_1
    jmp LBB0_3
LBB0_3:
    movl    -4(%rbp), %eax
    addq    $16, %rsp
    popq    %rbp
    retq
    .cfi_endproc

    .section    __TEXT,__cstring,cstring_literals
L_.str:                                 ## @.str
    .asciz  "This is a loop\n"


.subsections_via_symbols

Notice the extra LBB0_3 subroutine generated from the do while code. We get the extra Jump Not Equal instruction because we need to check if the condition of the while expression has been met after the statements in the do block have been executed.

This was a helpful resource on Stack Overflow: while(true) / while(1) vs. for(;;)

As Igor Skochinsky mentions in the comments, compiling each program with optimizations (-O3) will give you the exact same assembly. While this exercise was done on tiny programs with no optimizations, in reality, both loops accomplish the same thing and (depending on the compiler) would probably generate the same assembly. In reality, it is very difficult (if not impossible) to differentiate between a loop which uses while(1) and do { } while(1), because they both do the same thing.

2
  • 6
    now try again with some optimization
    – Igor Skochinsky
    Nov 18 '16 at 8:19
  • @IgorSkochinsky Thanks, added a note about how both programs should compile to the same assembly with optimizations.
    – JAL
    Nov 19 '16 at 17:10

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.