Problems in my sprintf and uint64_t output

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
User avatar
mrjbom
Member
Member
Posts: 322
Joined: Sun Jul 21, 2019 7:34 am

Problems in my sprintf and uint64_t output

Post by mrjbom »

Hello.
I found an implementation of sprintf and string.h for my system, in general it works fine. But if I try to output multiple uint64_t numbers, then I get a problem in the form of incorrect and too large values.

The strange thing is that the first time I get the correct string, and the second time I output a value of the same type, I get the wrong output. There are no errors in itoaUINT64.

Here my test code.
Here string.h code.

Here is the conclusion the conclusion of this test

Code: Select all

first printf
ram_available = 133692416 bytes
ram_available = 545460846592 mbytes

second my output
133692416 bytes
127 mbytes

third printf
L 123 and L 1958505086976

fourth my output
123 and 456

five printf
i 123 and i 456

six printf
I 123 and I 456
Why is this happening?
User avatar
Velko
Member
Member
Posts: 153
Joined: Fri Oct 03, 2008 4:13 am
Location: Ogre, Latvia, EU

Re: Problems in my sprintf and uint64_t output

Post by Velko »

There are no errors in itoaUINT64.
But there's a bug in your strcpy().
If something looks overcomplicated, most likely it is.
User avatar
mrjbom
Member
Member
Posts: 322
Joined: Sun Jul 21, 2019 7:34 am

Re: Problems in my sprintf and uint64_t output

Post by mrjbom »

Velko wrote:
There are no errors in itoaUINT64.
But there's a bug in your strcpy().
I fixed a bug in strcpy, but it didn't solve the problem. The problem is something else and I don't know what.
Craze Frog
Member
Member
Posts: 368
Joined: Sun Sep 23, 2007 4:52 am

Re: Problems in my sprintf and uint64_t output

Post by Craze Frog »

Maybe something with va_list and va_arg and 64-bit numbers.
User avatar
iansjack
Member
Member
Posts: 4827
Joined: Sat Mar 31, 2012 3:07 am
Location: Chichester, UK

Re: Problems in my sprintf and uint64_t output

Post by iansjack »

Try single-step ping through your code in a debugger.
nullplan
Member
Member
Posts: 1911
Joined: Wed Aug 30, 2017 8:24 am

Re: Problems in my sprintf and uint64_t output

Post by nullplan »

You have your own stdarg.h. Not a good idea. Nix it. There is a version of it in your compiler, which should be used. If you must use your own stdarg.h, and you are using GCC, then please just do:

Code: Select all

typedef __builtin_va_list va_list;
#define va_start(x,y) __builtin_va_start(x,y)
#define va_copy(x,y) __builtin_va_copy(x,y)
#define va_arg(x,y) __builtin_va_arg(x,y)
#define va_end(x) __builtin_va_end(x)
It is in general impossible to implement your own standard header files. The C compiler will have those even in freestanding mode. If it doesn't, that's a sign of not using a cross-compiler, which you really should.

Same for your stdint.h and stddef.h. string.h should be fine, since you are in freestanding mode. Also, the stuff in stddef.h is normally defined in stdbool.h, and stddef.h contains a whole lot more than you put in it. Just use the compiler header files and you should be fine.
Carpe diem!
User avatar
mrjbom
Member
Member
Posts: 322
Joined: Sun Jul 21, 2019 7:34 am

Re: Problems in my sprintf and uint64_t output

Post by mrjbom »

Craze Frog wrote:Maybe something with va_list and va_arg and 64-bit numbers.
But the first time the number is displayed correctly.
User avatar
mrjbom
Member
Member
Posts: 322
Joined: Sun Jul 21, 2019 7:34 am

Re: Problems in my sprintf and uint64_t output

Post by mrjbom »

nullplan wrote:You have your own stdarg.h. Not a good idea. Nix it. There is a version of it in your compiler, which should be used.
I'm trying to compile the kernel and use libgcc from the compiler in it.
But I had such problems:

Code: Select all

Compile .c files...
Build ./source/kmain.c
In file included from ./source/lfbmemory/lfbmemory.h:6:0,
                 from ./source/kmain.c:1:
/home/emilia/os/i386-elf-4.9.1-Linux-x86_64/lib/gcc/i386-elf/4.9.1/include/stdint.h:9:26: fatal error: stdint.h: No such file or directory
 # include_next <stdint.h>
                          ^
compilation terminated.
Build ./source/more/more.c
Build ./source/lfbmemory/lfbmemory.c
In file included from ./source/lfbmemory/../lfbmemory/lfbmemory.h:6:0,
                 from ./source/lfbmemory/lfbmemory.c:1:
/home/emilia/os/i386-elf-4.9.1-Linux-x86_64/lib/gcc/i386-elf/4.9.1/include/stdint.h:9:26: fatal error: stdint.h: No such file or directory
 # include_next <stdint.h>
                          ^
compilation terminated.
Build ./source/textmodememory/textmodememory.c
In file included from ./source/textmodememory/textmodememory.h:6:0,
                 from ./source/textmodememory/textmodememory.c:1:
/home/emilia/os/i386-elf-4.9.1-Linux-x86_64/lib/gcc/i386-elf/4.9.1/include/stdint.h:9:26: fatal error: stdint.h: No such file or directory
 # include_next <stdint.h>
                          ^
compilation terminated.
Build ./source/inlineassembly/inlineassembly.c
In file included from ./source/inlineassembly/../inlineassembly/inlineassembly.h:6:0,
                 from ./source/inlineassembly/inlineassembly.c:1:
/home/emilia/os/i386-elf-4.9.1-Linux-x86_64/lib/gcc/i386-elf/4.9.1/include/stdint.h:9:26: fatal error: stdint.h: No such file or directory
 # include_next <stdint.h>
                          ^
compilation terminated.
Build ./source/interruptions/interruptions.c
In file included from ./source/interruptions/interruptions.h:6:0,
                 from ./source/interruptions/interruptions.c:1:
/home/emilia/os/i386-elf-4.9.1-Linux-x86_64/lib/gcc/i386-elf/4.9.1/include/stdint.h:9:26: fatal error: stdint.h: No such file or directory
 # include_next <stdint.h>
                          ^
compilation terminated.
Build ./source/memory/memory.c
In file included from ./source/memory/memory.h:6:0,
                 from ./source/memory/memory.c:1:
/home/emilia/os/i386-elf-4.9.1-Linux-x86_64/lib/gcc/i386-elf/4.9.1/include/stdint.h:9:26: fatal error: stdint.h: No such file or directory
 # include_next <stdint.h>
                          ^
compilation terminated.
Build ./source/debug/debug.c
In file included from ./source/debug/debug.h:6:0,
                 from ./source/debug/debug.c:1:
/home/emilia/os/i386-elf-4.9.1-Linux-x86_64/lib/gcc/i386-elf/4.9.1/include/stdint.h:9:26: fatal error: stdint.h: No such file or directory
 # include_next <stdint.h>
                          ^
compilation terminated.
Build ./source/devices/keyboard/keyboard.c
In file included from ./source/devices/keyboard/keyboard.h:6:0,
                 from ./source/devices/keyboard/keyboard.c:1:
/home/emilia/os/i386-elf-4.9.1-Linux-x86_64/lib/gcc/i386-elf/4.9.1/include/stdint.h:9:26: fatal error: stdint.h: No such file or directory
 # include_next <stdint.h>
                          ^
compilation terminated.
Build ./source/devices/cpu/cpu.c
In file included from ./source/devices/cpu/../../debug/debug.h:6:0,
                 from ./source/devices/cpu/cpu.c:31:
/home/emilia/os/i386-elf-4.9.1-Linux-x86_64/lib/gcc/i386-elf/4.9.1/include/stdint.h:9:26: fatal error: stdint.h: No such file or directory
 # include_next <stdint.h>
                          ^
compilation terminated.
I use this script to compile.

What's wrong? How to fix it?
Last edited by mrjbom on Fri Dec 20, 2019 4:59 pm, edited 3 times in total.
User avatar
mrjbom
Member
Member
Posts: 322
Joined: Sun Jul 21, 2019 7:34 am

Re: Problems in my sprintf and uint64_t output

Post by mrjbom »

nullplan wrote:You have your own stdarg.h. Not a good idea. Nix it. There is a version of it in your compiler, which should be used.
I agree with you.
I want to use the standard compiler library instead of writing everything myself.
How can I change the way I compile in order not to write a standard library but to use that compiler?

Now I compile everything like this script.
User avatar
Solar
Member
Member
Posts: 7615
Joined: Thu Nov 16, 2006 12:01 pm
Location: Germany
Contact:

Re: Problems in my sprintf and uint64_t output

Post by Solar »

nullplan wrote:It is in general impossible to implement your own standard header files.
Ahem. It's certainly ill-advised unless you're in the business of implementing a standard library, but it is also certainly possible.
Every good solution is obvious once you've found it.
nullplan
Member
Member
Posts: 1911
Joined: Wed Aug 30, 2017 8:24 am

Re: Problems in my sprintf and uint64_t output

Post by nullplan »

mrjbom wrote: I use this script to compile.

What's wrong? How to fix it?
You changed that script since yesterday. Look into the file that is giving you problems, my copy of it only includes another stdint.h in hosted mode. Else it will include the stdint-gcc.h. So, if you just set the compiler to freestanding (which you did until yesterday), the problem should go away. And you have to set it to freestanding, since your kernel is not in a hosted environment.
Solar wrote:Ahem. It's certainly ill-advised unless you're in the business of implementing a standard library, but it is also certainly possible.
For the hosted headers, yes. The freestanding ones however usually require compiler magic to implement. You cannot in general know which basic type is signed and has the width of a pointer, but GCC will helpfully predefine __PTRDIFF_T__ for you (Edit: Sorry, I meant __PTRDIFF_TYPE__). That sort of thing. And stdarg.h can only be implemented as compiler magic (the GCC version being given above).

Of course, if you like needless work, you can have a stdint.h for every single ABI you can support. Or you can just use the compiler version, your call.
Carpe diem!
User avatar
mrjbom
Member
Member
Posts: 322
Joined: Sun Jul 21, 2019 7:34 am

Re: Problems in my sprintf and uint64_t output

Post by mrjbom »

nullplan wrote:
mrjbom wrote: I use this script to compile.

What's wrong? How to fix it?
You changed that script since yesterday. Look into the file that is giving you problems, my copy of it only includes another stdint.h in hosted mode. Else it will include the stdint-gcc.h. So, if you just set the compiler to freestanding (which you did until yesterday), the problem should go away. And you have to set it to freestanding, since your kernel is not in a hosted environment.
I added -ffreestanding to gcc at compile time of the files. Now it does not find some standard library header files like stdlib.h. What should I do? Are there any replacements in the cross-compiler?
Octocontrabass
Member
Member
Posts: 5882
Joined: Mon Mar 25, 2013 7:01 pm

Re: Problems in my sprintf and uint64_t output

Post by Octocontrabass »

mrjbom wrote:Now it does not find some standard library header files like stdlib.h. What should I do?
Stop including stdlib.h and see what definitions you're missing. You may need to include a different header, or you may need to come up with your own definitions. We have a list of freestanding headers here. You can use any of those headers in your kernel.
User avatar
mrjbom
Member
Member
Posts: 322
Joined: Sun Jul 21, 2019 7:34 am

Re: Problems in my sprintf and uint64_t output

Post by mrjbom »

Craze Frog wrote:Maybe something with va_list and va_arg and 64-bit numbers.
That's definitely the problem. va_list in any does not want to work with them.
Post Reply