在NASM中调用C函数时遇到问题

在NASM中调用C函数时遇到问题,c,assembly,nasm,C,Assembly,Nasm,我正在创建一个NASM程序,但我在NASM代码中调用C函数来简化我的生活。但我有未定义的引用错误。我做错了什么?代码如下: 我用来编译的命令行命令 nasm -fwin32 calculator.asm gcc - Wall -c print.c -o print.obj $ ld calculator.obj print.obj -o calculator.exe calculator.obj:calculator.asm:(.text+0x6): undefined refe

我正在创建一个NASM程序,但我在NASM代码中调用C函数来简化我的生活。但我有未定义的引用错误。我做错了什么?代码如下:

我用来编译的命令行命令

nasm -fwin32 calculator.asm    

gcc - Wall -c print.c -o print.obj

$ ld calculator.obj print.obj -o calculator.exe


calculator.obj:calculator.asm:(.text+0x6): undefined reference to `print'
calculator.obj:calculator.asm:(.text+0x15): undefined reference to `sum'
calculator.obj:calculator.asm:(.text+0x24): undefined reference to `int2string'
calculator.obj:calculator.asm:(.text+0x2a): undefined reference to `print'
calculator.obj:calculator.asm:(.text+0x2f): undefined reference to `ps'
print.obj:print.c:(.text+0xd): undefined reference to `printf'
print.obj:print.c:(.text+0x20): undefined reference to `atoi'
print.obj:print.c:(.text+0x8b): undefined reference to `printf'
print.obj:print.c:(.text+0xbe): undefined reference to `system'
#include <stdio.h>
#include <stdlib.h>

//Prototypes
void _print(char* string);
int _string2int(char* string);
char* _int2string(int i);
int _sum(int x, int y);
int _sub(int x, int y);
int _divide(int x, int y);
int _multiply(int x, int y);
void _pause();
char* itoa(int val, int base);

void print(char* string)
{
    printf(string);
}
int string2int(char* string)
{
    return atoi(string);
}
char* int2string(int i)
{
    return itoa(i, 10);
}
int subtract(int x, int y)
{
    return x + y;
}
int sub(int x, int y)
{
    return x - y;
}
int divide(int x, int y)
{
    if (y != 0)
    {
        return (x / y);
    }
    else if (y != 0)
    {
        printf("Infinity!");
        return 0;
    }
    return 0;
}
int multiply(int x, int y)
{
    return x * y;
}
void ps()
{
    system("Pause");
}
char* itoa(int val, int base){

    static char buf[32] = {0};

    int i = 30;

    for(; val && i ; --i, val /= base)

        buf[i] = "0123456789abcdef"[val % base];

    return &buf[i+1];

}
global _main
extern print
extern sum
extern subtract
extern divide
extern string2int
extern int2string
extern ps
section .data 

;Constant
message: db 'The sum of 2 + 2 is ', 0 

section .bss

;Variables
answer: resb 255
stranswer: resb 255

section .text
_main:

;Call the print function and print the variable named message.
push message
call print

;Add 2 and 2 and the return value gets placed in the eax register.
push 2
push 2

call sum
mov [answer], eax


push answer
call int2string

push eax
call print

;Pauses the console window.
call ps
平台

Windows 7 64位,但我是用32位编译的。这应该不是问题;我想

C代码

nasm -fwin32 calculator.asm    

gcc - Wall -c print.c -o print.obj

$ ld calculator.obj print.obj -o calculator.exe


calculator.obj:calculator.asm:(.text+0x6): undefined reference to `print'
calculator.obj:calculator.asm:(.text+0x15): undefined reference to `sum'
calculator.obj:calculator.asm:(.text+0x24): undefined reference to `int2string'
calculator.obj:calculator.asm:(.text+0x2a): undefined reference to `print'
calculator.obj:calculator.asm:(.text+0x2f): undefined reference to `ps'
print.obj:print.c:(.text+0xd): undefined reference to `printf'
print.obj:print.c:(.text+0x20): undefined reference to `atoi'
print.obj:print.c:(.text+0x8b): undefined reference to `printf'
print.obj:print.c:(.text+0xbe): undefined reference to `system'
#include <stdio.h>
#include <stdlib.h>

//Prototypes
void _print(char* string);
int _string2int(char* string);
char* _int2string(int i);
int _sum(int x, int y);
int _sub(int x, int y);
int _divide(int x, int y);
int _multiply(int x, int y);
void _pause();
char* itoa(int val, int base);

void print(char* string)
{
    printf(string);
}
int string2int(char* string)
{
    return atoi(string);
}
char* int2string(int i)
{
    return itoa(i, 10);
}
int subtract(int x, int y)
{
    return x + y;
}
int sub(int x, int y)
{
    return x - y;
}
int divide(int x, int y)
{
    if (y != 0)
    {
        return (x / y);
    }
    else if (y != 0)
    {
        printf("Infinity!");
        return 0;
    }
    return 0;
}
int multiply(int x, int y)
{
    return x * y;
}
void ps()
{
    system("Pause");
}
char* itoa(int val, int base){

    static char buf[32] = {0};

    int i = 30;

    for(; val && i ; --i, val /= base)

        buf[i] = "0123456789abcdef"[val % base];

    return &buf[i+1];

}
global _main
extern print
extern sum
extern subtract
extern divide
extern string2int
extern int2string
extern ps
section .data 

;Constant
message: db 'The sum of 2 + 2 is ', 0 

section .bss

;Variables
answer: resb 255
stranswer: resb 255

section .text
_main:

;Call the print function and print the variable named message.
push message
call print

;Add 2 and 2 and the return value gets placed in the eax register.
push 2
push 2

call sum
mov [answer], eax


push answer
call int2string

push eax
call print

;Pauses the console window.
call ps

结论:很抱歉发了这么长的帖子

您的ps函数没有声明,sum也没有定义。有两个函数sub和subtract。我猜你希望其中一个是sum。最后四个原因是没有链接libc。

您的ps函数没有声明,sum也没有定义。有两个函数sub和subtract。我猜你希望其中一个是sum。最后四个是因为没有链接libc。

最后四个是因为没有链接libc。仅供参考:您的
subtract
函数命名错误。它返回
x+y
。另外,您正在asm中使用
stdcall
,但是它们被定义为
cdecl
,为什么在C文件中有大量带有
\ucode>前缀的原型?那没有任何意义。在汇编代码中的extern指令中不需要
\uu
前缀吗?最后四个是因为您没有在libc.FYI中链接:您的
subtract
函数命名错误。它返回
x+y
。另外,您正在asm中使用
stdcall
,但是它们被定义为
cdecl
,为什么在C文件中有大量带有
\ucode>前缀的原型?那没有任何意义。在汇编代码中的extern指令中不需要前缀
\uuu
?可以在ld命令中使用-lglibc或快捷方式-lc,它应该可以完成此任务。可以在ld命令中使用-lglibc或快捷方式-lc,它应该完成此任务。