Problem converting meaty skeleton to work with CPP

Question about which tools to use, bugs, the best way to implement a function, etc should go here. Don't forget to see if your question is answered in the wiki first! When in doubt post here.
Post Reply
heavyweight87
Posts: 22
Joined: Sun Apr 28, 2019 7:39 am

Problem converting meaty skeleton to work with CPP

Post by heavyweight87 »

Hi,

I would like to start taking the meaty skeleton project and change the kernel.c to kernel.cpp
I took the meaty skeleton project and changed a few things so it would work with cpp:

* I renamed kernel.c to kernel.cpp
* I added extern "C" on function prototypes where needed
* I added export CPP=${HOST}-g++ to config.sh
* I added ffreestanding -nostdlib -fno-exceptions -fno-rtti to CCFLAGS in the makefile
* I added this to the makefil:
.cpp.o:
$(CPP) -MD $(CPPFLAGS) $< -o $@

The problem is I get undefined refernces to any external functions e.g. printf, serial_init, terminal_initialize

Im sure the problem is quite basic but I have less experience with C++ and makefiles

A repository with the changes I did is here:
https://github.com/heavyweight87/SakuraOS/tree/cpp

Any ideas?
mallard
Member
Member
Posts: 280
Joined: Tue May 13, 2014 3:02 am
Location: Private, UK

Re: Problem converting meaty skeleton to work with CPP

Post by mallard »

Make sure you've deleted any old .o files that may have been generated from C compilation.

Are the external functions that you're having problems with declared as 'extern "C"' or not? Are they defined in C or C++ code? Could you post the complete compiler/linker output?
Image
heavyweight87
Posts: 22
Joined: Sun Apr 28, 2019 7:39 am

Re: Problem converting meaty skeleton to work with CPP

Post by heavyweight87 »

Yeh I made sure I did a clean before.
I wrapped the function prototypes in the .h file with the extern "C".

output from the compiler:


mkdir -p /home/gcb/Projects/myos/SakuraOS/sysroot/usr/include
cp -R --preserve=timestamps include/. /home/gcb/Projects/myos/SakuraOS/sysroot/usr/include/.
mkdir -p /home/gcb/Projects/myos/SakuraOS/sysroot/usr/include
cp -R --preserve=timestamps include/. /home/gcb/Projects/myos/SakuraOS/sysroot/usr/include/.
mkdir -p /home/gcb/Projects/myos/SakuraOS/sysroot/usr/include
cp -R --preserve=timestamps include/. /home/gcb/Projects/myos/SakuraOS/sysroot/usr/include/.
mkdir -p /home/gcb/Projects/myos/SakuraOS/sysroot/usr/lib
cp libk.a /home/gcb/Projects/myos/SakuraOS/sysroot/usr/lib
mkdir -p /home/gcb/Projects/myos/SakuraOS/sysroot/usr/include
cp -R --preserve=timestamps include/. /home/gcb/Projects/myos/SakuraOS/sysroot/usr/include/.
i686-elf-g++ --sysroot=/home/gcb/Projects/myos/SakuraOS/sysroot -isystem=/usr/include -MD -O0 -g -D__is_kernel -Iinclude -ffreestanding -nostdlib -Wall -Wextra -fno-exceptions -fno-rtti kernel/kernel.cpp -o kernel/kernel.o
kernel/kernel.cpp: In function 'int kernel_main(uint32_t, multiboot_info_t*)':
kernel/kernel.cpp:89:37: warning: array subscript has type 'char' [-Wchar-subscripts]
printf("%c", kbdus[x]);
^
/home/gcb/opt/cross/lib/gcc/i686-elf/7.4.0/../../../../i686-elf/bin/ld: warning: cannot find entry symbol _start; defaulting to 0000000008048074
/home/gcb/opt/cross/lib/gcc/i686-elf/7.4.0/../../../../i686-elf/bin/ld: /tmp/ccZo95GY.o: in function `load_modules(multiboot_info*)':
/home/gcb/Projects/myos/SakuraOS/kernel/kernel/kernel.cpp:56: undefined reference to `printf'
/home/gcb/opt/cross/lib/gcc/i686-elf/7.4.0/../../../../i686-elf/bin/ld: /tmp/ccZo95GY.o: in function `kernel_main(unsigned long, multiboot_info*)':
/home/gcb/Projects/myos/SakuraOS/kernel/kernel/kernel.cpp:67: undefined reference to `terminal_initialize'
/home/gcb/opt/cross/lib/gcc/i686-elf/7.4.0/../../../../i686-elf/bin/ld: /home/gcb/Projects/myos/SakuraOS/kernel/kernel/kernel.cpp:68: undefined reference to `serial_init'
/home/gcb/opt/cross/lib/gcc/i686-elf/7.4.0/../../../../i686-elf/bin/ld: /home/gcb/Projects/myos/SakuraOS/kernel/kernel/kernel.cpp:69: undefined reference to `printf'
/home/gcb/opt/cross/lib/gcc/i686-elf/7.4.0/../../../../i686-elf/bin/ld: /home/gcb/Projects/myos/SakuraOS/kernel/kernel/kernel.cpp:72: undefined reference to `printf'
/home/gcb/opt/cross/lib/gcc/i686-elf/7.4.0/../../../../i686-elf/bin/ld: /home/gcb/Projects/myos/SakuraOS/kernel/kernel/kernel.cpp:75: undefined reference to `printf'
/home/gcb/opt/cross/lib/gcc/i686-elf/7.4.0/../../../../i686-elf/bin/ld: /home/gcb/Projects/myos/SakuraOS/kernel/kernel/kernel.cpp:89: undefined reference to `printf'
User avatar
bellezzasolo
Member
Member
Posts: 110
Joined: Sun Feb 20, 2011 2:01 pm

Re: Problem converting meaty skeleton to work with CPP

Post by bellezzasolo »

heavyweight87 wrote:Yeh I made sure I did a clean before.
I wrapped the function prototypes in the .h file with the extern "C".

output from the compiler:


mkdir -p /home/gcb/Projects/myos/SakuraOS/sysroot/usr/include
cp -R --preserve=timestamps include/. /home/gcb/Projects/myos/SakuraOS/sysroot/usr/include/.
mkdir -p /home/gcb/Projects/myos/SakuraOS/sysroot/usr/include
cp -R --preserve=timestamps include/. /home/gcb/Projects/myos/SakuraOS/sysroot/usr/include/.
mkdir -p /home/gcb/Projects/myos/SakuraOS/sysroot/usr/include
cp -R --preserve=timestamps include/. /home/gcb/Projects/myos/SakuraOS/sysroot/usr/include/.
mkdir -p /home/gcb/Projects/myos/SakuraOS/sysroot/usr/lib
cp libk.a /home/gcb/Projects/myos/SakuraOS/sysroot/usr/lib
mkdir -p /home/gcb/Projects/myos/SakuraOS/sysroot/usr/include
cp -R --preserve=timestamps include/. /home/gcb/Projects/myos/SakuraOS/sysroot/usr/include/.
i686-elf-g++ --sysroot=/home/gcb/Projects/myos/SakuraOS/sysroot -isystem=/usr/include -MD -O0 -g -D__is_kernel -Iinclude -ffreestanding -nostdlib -Wall -Wextra -fno-exceptions -fno-rtti kernel/kernel.cpp -o kernel/kernel.o
kernel/kernel.cpp: In function 'int kernel_main(uint32_t, multiboot_info_t*)':
kernel/kernel.cpp:89:37: warning: array subscript has type 'char' [-Wchar-subscripts]
printf("%c", kbdus[x]);
^
/home/gcb/opt/cross/lib/gcc/i686-elf/7.4.0/../../../../i686-elf/bin/ld: warning: cannot find entry symbol _start; defaulting to 0000000008048074
/home/gcb/opt/cross/lib/gcc/i686-elf/7.4.0/../../../../i686-elf/bin/ld: /tmp/ccZo95GY.o: in function `load_modules(multiboot_info*)':
/home/gcb/Projects/myos/SakuraOS/kernel/kernel/kernel.cpp:56: undefined reference to `printf'
/home/gcb/opt/cross/lib/gcc/i686-elf/7.4.0/../../../../i686-elf/bin/ld: /tmp/ccZo95GY.o: in function `kernel_main(unsigned long, multiboot_info*)':
/home/gcb/Projects/myos/SakuraOS/kernel/kernel/kernel.cpp:67: undefined reference to `terminal_initialize'
/home/gcb/opt/cross/lib/gcc/i686-elf/7.4.0/../../../../i686-elf/bin/ld: /home/gcb/Projects/myos/SakuraOS/kernel/kernel/kernel.cpp:68: undefined reference to `serial_init'
/home/gcb/opt/cross/lib/gcc/i686-elf/7.4.0/../../../../i686-elf/bin/ld: /home/gcb/Projects/myos/SakuraOS/kernel/kernel/kernel.cpp:69: undefined reference to `printf'
/home/gcb/opt/cross/lib/gcc/i686-elf/7.4.0/../../../../i686-elf/bin/ld: /home/gcb/Projects/myos/SakuraOS/kernel/kernel/kernel.cpp:72: undefined reference to `printf'
/home/gcb/opt/cross/lib/gcc/i686-elf/7.4.0/../../../../i686-elf/bin/ld: /home/gcb/Projects/myos/SakuraOS/kernel/kernel/kernel.cpp:75: undefined reference to `printf'
/home/gcb/opt/cross/lib/gcc/i686-elf/7.4.0/../../../../i686-elf/bin/ld: /home/gcb/Projects/myos/SakuraOS/kernel/kernel/kernel.cpp:89: undefined reference to `printf'
It looks like you're referencing extern C functions that aren't there. Have you made the functions themselves extern "C", rather than just the prototypes?
Whoever said you can't do OS development on Windows?
https://github.com/ChaiSoft/ChaiOS
heavyweight87
Posts: 22
Joined: Sun Apr 28, 2019 7:39 am

Re: Problem converting meaty skeleton to work with CPP

Post by heavyweight87 »

I thought the extern "C" only went around the prototype?
I tried adding it to the function definition and it didn't change anything...

More than that __cplusplus is never defined in printf.c for example .I guess that makes sense no?

The strange thing is that all the object files are present, so im not sure why it can't find the functions
mallard
Member
Member
Posts: 280
Joined: Tue May 13, 2014 3:02 am
Location: Private, UK

Re: Problem converting meaty skeleton to work with CPP

Post by mallard »

heavyweight87 wrote: More than that __cplusplus is never defined in printf.c for example .I guess that makes sense no?
Yes, "__cplusplus" will only be defined in C++ code. Never in C code. Differentiating between C and C++ compilers is pretty much what it's for. I assume therefore you have the 'extern "C"' in the .h file wrapped in "#ifdef __cplusplus" so that it doesn't upset the C compiler?

Is "kernel.cpp" actually including the same .h file that contains the 'extern "C"' definitions? I presume you haven't done something like writing the definitions directly into the source file...
Image
heavyweight87
Posts: 22
Joined: Sun Apr 28, 2019 7:39 am

Re: Problem converting meaty skeleton to work with CPP

Post by heavyweight87 »

so for example, kernel.cpp references serial.h
(you can see here: https://github.com/heavyweight87/Sakura ... l/serial.h)

serial.h looks like this:

Code: Select all

#ifndef __KERNEL_SERIAL_H_
#define __KERNEL_SERIAL_H_

#ifdef __cplusplus
extern "C" {
#endif

void serial_init(void);
void serial_printchar(char a);
int serial_printf(const char* __restrict format, ...);

#ifdef __cplusplus
}
#endif

#endif //__KERNEL_SERIAL_H_
heavyweight87
Posts: 22
Joined: Sun Apr 28, 2019 7:39 am

Re: Problem converting meaty skeleton to work with CPP

Post by heavyweight87 »

I found the problem

I added this to the makefile:
.cpp.o:
$(CPP) -MD $(CPPFLAGS) $< -o $@

but I missed the -c flag which tells gcc to compile without linking

Thanks for your help, everything works fine :)
Post Reply