I am writing a program in MASM assembly. There are two files: one is an a.asm file and the other is a c.cpp file. The assembly program contains a function named asm_01. This function calls the printf and scanf functions from C. The intention is to prompt the user to enter an integer using printf, receive the input using scanf, and then print the number again using printf. The asm_01 function is called from the main function in C++.
This is what I am expecting when I execute the .exe file
Please enter a number : [Use will enter the number]
Number entered by you is : [Number will be displayed here]
Code of c.cpp i.e. the C++ code is given below…
#include <stdio.h>
#include <stdlib.h>
extern "C" {
void asm_01(void);
}
int main(int argc, char *argv[]) {
asm_01();
return 0;
}
Code of a.asm i.e. the assembly code is given below…
option casemap:none
.data
d1 qword 0
s1 byte "Please enter a number : ", 0
s2 byte "%ld", 0
s3 byte "Number entered by you : %d", 10, 0
.code
externdef printf:proc
externdef scanf:proc
asm_01 proc
sub rsp, 56
lea rcx, s1
call printf
lea rcx, s2
lea rdx, d1
call scanf
lea rcx, s3
mov rdx, d1
call printf
add rsp, 56
ret
asm_01 endp
end
I have compiled the file a.asm with ml64.exe as ml64.exe /c a.asm which generates the a.obj file.
But when I compiled the C++ file with the a.obj file the following error comes…
$cl.exe c.cpp a.obj
Microsoft (R) C/C++ Optimizing Compiler Version 19.xx.xxxx for x64
Copyright (C) Microsoft Corporation. All rights reserved.
c.cpp
Microsoft (R) Incremental Linker Version 14.xx.xxxx.0
Copyright (C) Microsoft Corporation. All rights reserved.
/out:c.exe
c.obj
a.obj
a.obj : error LNK2019: unresolved external symbol scanf referenced in function asm_01
c.exe : fatal error LNK1120: 1 unresolved externals
If I remove the scanf part from the assembly program, the printf function works fine. I am aware that there are alternative methods to accept input in assembly, but I specifically want to use scanf. In the assembly code, I’ve loaded the format string’s address and the qword ‘d1’ address into the rcx and rdx registers, following Microsoft’s ABI. Despite this, it’s not functioning as expected. What I am missing here. Please help. Thanks.
I am using Windows OS and MASM.