Writing Hello World in C++ Without Including Anything

Mostly for my own amusement: how to invoke a system call on Linux to write "Hello world" to the screen, without going through C's puts(), C++'s iostreams, or even glibc's write().

int main() {
  constexpr char data[] = "Hello world\n";
  constexpr auto size = sizeof data;
  asm volatile (
    "movq $1, %%rax \n\t"  // 1 is the constant for SYS_write
    "movq $1, %%rdi \n\t"  // 1 is the constant for stdout
    "movq %0, %%rsi \n\t"  // Our pointer
    "movq %1, %%rdx \n\t"  // Our size
    "syscall"              // Execute
  :                        // No output variables
  : "r"(data)              // Inputs: pass data via a register
  , "i"(size)              //         pass size as if it were a constant
  : "%rax", "%rdi", "%rsi", "%rdx" // The registers we clobber
  );
}

The general form of this funky block is:

asm volatile(
      template,
      : inputs
      : outputs
      : clobbers
 );

The "r" in front of the first output means "pass this in a register". The "i" in front of the second output means "treat this as a constant". There are many other such labels. Inputs and outputs can be referenced via %0, %1, ... . Outputs are listed first. Here, since we do not declare outputs, %0 refers to our first input.

Compiling this with gcc on Debian 13 results in the following assembly output (you can see precisely where it spliced in our exact assembly code):

	.file	"test.cpp"
	.text
	.globl	main
	.type	main, @function
main:
.LFB0:
	.cfi_startproc
	pushq	%rbp
	.cfi_def_cfa_offset 16
	.cfi_offset 6, -16
	movq	%rsp, %rbp
	.cfi_def_cfa_register 6
	movabsq	$8031924123371070792, %rax
	movq	%rax, -21(%rbp)
	movabsq	$2925166706259744, %rax
	movq	%rax, -16(%rbp)
	movq	$13, -8(%rbp)
	leaq	-21(%rbp), %rcx
	movl	$13, %r8d
#APP
# 5 "test.cpp" 1
	movq $1, %rax
        movq $1, %rdi
        movq %rcx, %rsi
        movq %r8, %rdx
        syscall
# 0 "" 2
#NO_APP
	movl	$0, %eax
	popq	%rbp
	.cfi_def_cfa 7, 8
	ret
	.cfi_endproc
.LFE0:
	.size	main, .-main
	.ident	"GCC: (Debian 14.2.0-19) 14.2.0"
	.section	.note.GNU-stack,"",@progbits
    

Pretty neat, eh.


Back to my homepage...