对外部函数的未定义引用 - C
Undefined reference to extern function - C
我目前正在做一个 C 项目,但我被困在一个看似简单的问题上...
我的文件是 main.c, main.h, fun1.c 、fun2.c 和 fun3.c.
main.h包含在main.c,fun1,fun2,fun3(分别在fun1.C、fun2.c 和 fun3.c 文件)被 a main.c 中的函数,fun1、fun2 和 fun3 函数在 main.h 中声明如下:
extern int fun1(unsigned);
extern int fun2(int, int, int);
extern int fun3(int, int);
但是当我尝试编译代码时,出现了这些错误
main.c:12: undefined reference to 'fun1'
main.c:17: undefined reference to 'fun2'
main.c:25: undefined reference to 'fun3'
我是否错过了有关 extern
工作方式的某些信息?感谢您的回答。
这个项目实际上要复杂得多,因为我正在研究内核,但我简化了它。这是我老师给我的作品,我尽量少修改代码,所以我坚持使用extern
.
更新
由于问题似乎出在其他地方,我将向您展示我的文件系统。
我的文件是 sem.c, sem.h, semget.c 、semctl.c 和 semop.c.
sem.h包含在sem.c、semget、semctl和semop(分别在semget.C、semctl.c 和 semop.c 文件)被 a sem.c中的函数,semget、semctl和semop函数在sem.h中声明为extern(同前) ,只是改回了名称)。
在makefile中的某个点(不要问我makefile在做什么,我不知道因为它的复杂性),文件syscalls.c使用:
#include <nanvix/const.h>
#include <nanvix/syscall.h>
/*
* System calls table.
*/
PUBLIC void (*syscalls_table[NR_SYSCALLS])(void) = {
(void (*)(void))&sys_alarm,
...
(void (*)(void))&semget,
(void (*)(void))&semctl,
(void (*)(void))&semop
};
syscalls.c 文件包含 syscall.h 文件:
#ifndef NANVIX_SYSCALL_H_
#define NANVIX_SYSCALL_H_
#include <nanvix/const.h>
#include <signal.h>
#include <sys/stat.h>
#include <sys/times.h>
#include <sys/types.h>
#include <sys/utsname.h>
#include <ustat.h>
#include <utime.h>
/* Number of system calls. */
#define NR_SYSCALLS 51
/* System call numbers. */
#define NR_alarm 0
#define NR_brk 1
...
#define NR_semget 48
#define NR_semctl 49
#define NR_semop 50
#ifndef _ASM_FILE_
/* System calls prototypes. */
EXTERN unsigned sys_alarm(unsigned seconds);
EXTERN int sys_brk(void *ptr);
...
EXTERN int semget(unsigned key);
EXTERN int semctl(int semid, int cmd, int val);
EXTERN int semop(int semid, int op);
#endif /* _ASM_FILE_ */
#endif /* NANVIX_SYSCALL_H_ */
具体错误如下:
sys/syscalls.o:(.data+0xc0): undefined reference to `semget'
sys/syscalls.o:(.data+0xc4): undefined reference to `semctl'
sys/syscalls.o:(.data+0xc8): undefined reference to `semop'
sys/sem.o: In function `create':
/home/windea/workshop/ricm4/as/nanvix/src/kernel/sys/sem.c:12: undefined reference to `semget'
/home/windea/workshop/ricm4/as/nanvix/src/kernel/sys/sem.c:17: undefined reference to `semctl'
sys/sem.o: In function `down':
/home/windea/workshop/ricm4/as/nanvix/src/kernel/sys/sem.c:25: undefined reference to `semop'
sys/sem.o: In function `up':
/home/windea/workshop/ricm4/as/nanvix/src/kernel/sys/sem.c:33: undefined reference to `semop'
sys/sem.o: In function `destroy':
/home/windea/workshop/ricm4/as/nanvix/src/kernel/sys/sem.c:41: undefined reference to `semctl'
makefile:67: recipe for target 'all' failed
make[2]: *** [all] Error 1
最后,make
在出错前最后执行的命令行是:
i386-elf-ld -T arch/x86/link.ld arch/x86/utilities.o arch/x86/io.o arch/x86/boot.o arch/x86/hooks.o arch/x86/setup.o arch/x86/hwint.o arch/x86/8259.o arch/x86/exception.o arch/x86/clock.o arch/x86/hal.o dev/dev.o dev/ata/ata.o dev/klog/klog.o dev/ramdisk/ramdisk.o dev/tty/console.o dev/tty/keyboard.o dev/tty/tty.o fs/file.o fs/block.o fs/super.o fs/buffer.o fs/pipe.o fs/inode.o fs/fs.o init/main.o lib/kstrncpy.o lib/kpanic.o lib/kprintf.o lib/kvsprintf.o lib/krand.o lib/kmemcpy.o lib/ksrand.o lib/kmemdump.o lib/kstrlen.o lib/kstrcmp.o lib/kstrcpy.o lib/kmemset.o lib/kstrncmp.o lib/bitmap.o mm/mm.o mm/paging.o mm/region.o pm/die.o pm/sleep.o pm/pm.o pm/sched.o pm/signal.o sys/times.o sys/stat.o sys/setgid.o sys/alarm.o sys/shutdown.o sys/kill.o sys/chmod.o sys/ioctl.o sys/umask.o sys/close.o sys/_exit.o sys/ustat.o sys/setegid.o sys/getgid.o sys/fork.o sys/getpgrp.o sys/nice.o sys/chroot.o sys/brk.o sys/syscalls.o sys/ps.o sys/wait.o sys/sync.o sys/unlink.o sys/setpgrp.o sys/signal.o sys/pause.o sys/link.o sys/read.o sys/gticks.o sys/fcntl.o sys/utime.o sys/write.o sys/geteuid.o sys/chdir.o sys/pipe.o sys/getegid.o sys/setuid.o sys/access.o sys/execve.o sys/getppid.o sys/chown.o sys/uname.o sys/lseek.o sys/sem.o sys/open.o sys/seteuid.o sys/getuid.o sys/getpid.o -o /home/windea/workshop/ricm4/as/nanvix/bin/kernel
我不知道这是否会帮助任何人理解我的问题,但现在我认为你至少可以更好地了解发生了什么。
看起来您只编译了 main.c 而不是 fun1.c、fun2.c 和 fun3.c
你可以尝试编译如下:
gcc -c main.c -o main.o
gcc -c fun1.c -o fun1.o
gcc -c fun2.c -o fun2.o
gcc -c fun3.c -o fun3.o
gcc main.o fun1.o fun2.o fun3.o -o all.out
我目前正在做一个 C 项目,但我被困在一个看似简单的问题上...
我的文件是 main.c, main.h, fun1.c 、fun2.c 和 fun3.c.
main.h包含在main.c,fun1,fun2,fun3(分别在fun1.C、fun2.c 和 fun3.c 文件)被 a main.c 中的函数,fun1、fun2 和 fun3 函数在 main.h 中声明如下:
extern int fun1(unsigned);
extern int fun2(int, int, int);
extern int fun3(int, int);
但是当我尝试编译代码时,出现了这些错误
main.c:12: undefined reference to 'fun1'
main.c:17: undefined reference to 'fun2'
main.c:25: undefined reference to 'fun3'
我是否错过了有关 extern
工作方式的某些信息?感谢您的回答。
这个项目实际上要复杂得多,因为我正在研究内核,但我简化了它。这是我老师给我的作品,我尽量少修改代码,所以我坚持使用extern
.
更新
由于问题似乎出在其他地方,我将向您展示我的文件系统。
我的文件是 sem.c, sem.h, semget.c 、semctl.c 和 semop.c.
sem.h包含在sem.c、semget、semctl和semop(分别在semget.C、semctl.c 和 semop.c 文件)被 a sem.c中的函数,semget、semctl和semop函数在sem.h中声明为extern(同前) ,只是改回了名称)。
在makefile中的某个点(不要问我makefile在做什么,我不知道因为它的复杂性),文件syscalls.c使用:
#include <nanvix/const.h>
#include <nanvix/syscall.h>
/*
* System calls table.
*/
PUBLIC void (*syscalls_table[NR_SYSCALLS])(void) = {
(void (*)(void))&sys_alarm,
...
(void (*)(void))&semget,
(void (*)(void))&semctl,
(void (*)(void))&semop
};
syscalls.c 文件包含 syscall.h 文件:
#ifndef NANVIX_SYSCALL_H_
#define NANVIX_SYSCALL_H_
#include <nanvix/const.h>
#include <signal.h>
#include <sys/stat.h>
#include <sys/times.h>
#include <sys/types.h>
#include <sys/utsname.h>
#include <ustat.h>
#include <utime.h>
/* Number of system calls. */
#define NR_SYSCALLS 51
/* System call numbers. */
#define NR_alarm 0
#define NR_brk 1
...
#define NR_semget 48
#define NR_semctl 49
#define NR_semop 50
#ifndef _ASM_FILE_
/* System calls prototypes. */
EXTERN unsigned sys_alarm(unsigned seconds);
EXTERN int sys_brk(void *ptr);
...
EXTERN int semget(unsigned key);
EXTERN int semctl(int semid, int cmd, int val);
EXTERN int semop(int semid, int op);
#endif /* _ASM_FILE_ */
#endif /* NANVIX_SYSCALL_H_ */
具体错误如下:
sys/syscalls.o:(.data+0xc0): undefined reference to `semget'
sys/syscalls.o:(.data+0xc4): undefined reference to `semctl'
sys/syscalls.o:(.data+0xc8): undefined reference to `semop'
sys/sem.o: In function `create':
/home/windea/workshop/ricm4/as/nanvix/src/kernel/sys/sem.c:12: undefined reference to `semget'
/home/windea/workshop/ricm4/as/nanvix/src/kernel/sys/sem.c:17: undefined reference to `semctl'
sys/sem.o: In function `down':
/home/windea/workshop/ricm4/as/nanvix/src/kernel/sys/sem.c:25: undefined reference to `semop'
sys/sem.o: In function `up':
/home/windea/workshop/ricm4/as/nanvix/src/kernel/sys/sem.c:33: undefined reference to `semop'
sys/sem.o: In function `destroy':
/home/windea/workshop/ricm4/as/nanvix/src/kernel/sys/sem.c:41: undefined reference to `semctl'
makefile:67: recipe for target 'all' failed
make[2]: *** [all] Error 1
最后,make
在出错前最后执行的命令行是:
i386-elf-ld -T arch/x86/link.ld arch/x86/utilities.o arch/x86/io.o arch/x86/boot.o arch/x86/hooks.o arch/x86/setup.o arch/x86/hwint.o arch/x86/8259.o arch/x86/exception.o arch/x86/clock.o arch/x86/hal.o dev/dev.o dev/ata/ata.o dev/klog/klog.o dev/ramdisk/ramdisk.o dev/tty/console.o dev/tty/keyboard.o dev/tty/tty.o fs/file.o fs/block.o fs/super.o fs/buffer.o fs/pipe.o fs/inode.o fs/fs.o init/main.o lib/kstrncpy.o lib/kpanic.o lib/kprintf.o lib/kvsprintf.o lib/krand.o lib/kmemcpy.o lib/ksrand.o lib/kmemdump.o lib/kstrlen.o lib/kstrcmp.o lib/kstrcpy.o lib/kmemset.o lib/kstrncmp.o lib/bitmap.o mm/mm.o mm/paging.o mm/region.o pm/die.o pm/sleep.o pm/pm.o pm/sched.o pm/signal.o sys/times.o sys/stat.o sys/setgid.o sys/alarm.o sys/shutdown.o sys/kill.o sys/chmod.o sys/ioctl.o sys/umask.o sys/close.o sys/_exit.o sys/ustat.o sys/setegid.o sys/getgid.o sys/fork.o sys/getpgrp.o sys/nice.o sys/chroot.o sys/brk.o sys/syscalls.o sys/ps.o sys/wait.o sys/sync.o sys/unlink.o sys/setpgrp.o sys/signal.o sys/pause.o sys/link.o sys/read.o sys/gticks.o sys/fcntl.o sys/utime.o sys/write.o sys/geteuid.o sys/chdir.o sys/pipe.o sys/getegid.o sys/setuid.o sys/access.o sys/execve.o sys/getppid.o sys/chown.o sys/uname.o sys/lseek.o sys/sem.o sys/open.o sys/seteuid.o sys/getuid.o sys/getpid.o -o /home/windea/workshop/ricm4/as/nanvix/bin/kernel
我不知道这是否会帮助任何人理解我的问题,但现在我认为你至少可以更好地了解发生了什么。
看起来您只编译了 main.c 而不是 fun1.c、fun2.c 和 fun3.c
你可以尝试编译如下:
gcc -c main.c -o main.o
gcc -c fun1.c -o fun1.o
gcc -c fun2.c -o fun2.o
gcc -c fun3.c -o fun3.o
gcc main.o fun1.o fun2.o fun3.o -o all.out