#161380 - ferrand.d - Sat Aug 02, 2008 3:29 pm
Hello !
I am continuing the project LMP-ng, and i added SQLite to my project. Unfortunately, it needs some system functions to acces files, etc... that are not in my devkitARM environment.
The three functions i'm trying to rewrite are sleep, fsync and ftruncate. I've already rewritten sleep like that :
Code: |
unsigned sleep(unsigned int seconds)
{
int i, j;
for (i = 0; i < seconds; i++)
for (j = 0; j <60; j++)
swiWaitForVBlank();
return 0;
} |
Have you got ideas for the other functions ?
Thanks very much.
#161382 - Dwedit - Sat Aug 02, 2008 5:58 pm
Whenever you do an fflush or fclose, the file is synced to disk immediately, so fsync would probably be blank.
_________________
"We are merely sprites that dance at the beck and call of our button pressing overlord."
#161398 - silent_code - Sat Aug 02, 2008 11:21 pm
Your sleep function will only work for 60hz games, though it might be useful in some cases. :^)
_________________
July 5th 08: "Volumetric Shadow Demo" 1.6.0 (final) source released
June 5th 08: "Zombie NDS" WIP released!
It's all on my page, just click WWW below.
#161400 - DiscoStew - Sat Aug 02, 2008 11:32 pm
Since swiWatiForVBlank is fixed for ~60hz, would it make much of a difference?
_________________
DS - It's all about DiscoStew
#161403 - silent_code - Sat Aug 02, 2008 11:37 pm
What is the bahaviour with a 30hz game then? I don't have the time to test it now, it's bed time (0:36), so I hope you have the answer.
Also, I had kind of a s.y day, so my thinking machine is idle most of the time right now.
_________________
July 5th 08: "Volumetric Shadow Demo" 1.6.0 (final) source released
June 5th 08: "Zombie NDS" WIP released!
It's all on my page, just click WWW below.
#161406 - Dwedit - Sat Aug 02, 2008 11:57 pm
NDS doesn't have any PAL region, every NDS has a vblank time of 59.8261Hz.
But why do you need a Sleep function? Isn't calling sleep just a way to tell the OS that you want your process to give up its time slice? There's no OS on the DS, unless you count dslinux.
_________________
"We are merely sprites that dance at the beck and call of our button pressing overlord."
#161407 - silent_code - Sun Aug 03, 2008 12:08 am
In my current demo, the framrate is 30 hz (for now). Won't that affect anything?
I guess what you are trying to say is, that the interrupt will fire anyway, so it's still valid and independent of the frame rate.
In that case, I take back my comment.
Sorry! :^D
_________________
July 5th 08: "Volumetric Shadow Demo" 1.6.0 (final) source released
June 5th 08: "Zombie NDS" WIP released!
It's all on my page, just click WWW below.
#161414 - Lazy1 - Sun Aug 03, 2008 3:07 am
Dwedit wrote: |
NDS doesn't have any PAL region, every NDS has a vblank time of 59.8261Hz.
But why do you need a Sleep function? Isn't calling sleep just a way to tell the OS that you want your process to give up its time slice? There's no OS on the DS, unless you count dslinux. |
I think what he means is devkitARM does not provide some functions that are used by SQLite.
When I tried to get libsndfile on the ds it would not work because ftruncate is missing so I hope you find a good solution :D
#161415 - Dwedit - Sun Aug 03, 2008 3:14 am
Rephrasing: Why do you even need a NON BLANK sleep function?
_________________
"We are merely sprites that dance at the beck and call of our button pressing overlord."
#161419 - tepples - Sun Aug 03, 2008 4:03 am
If it's SQLite, I can see where these functions might be used. - ftruncate() is used for chopping off the end of a file that has become smaller without having to copy and rename. This might take place when a program runs VACUUM on a database to compact and repair it.
- fsync() is used to make sure that writes to a database or journal have actually taken effect on the storage medium (the D in ACID).
- I think SQLite might use sleep() for file locking: poll the file every second or so until it shows not locked or until a timeout expires. This is important for database files on a CIFS share, but libnds is most commonly used as a single-tasking operating environment incapable of mounting network shares, and a program on such a system might not need the locking.
_________________
-- Where is he?
-- Who?
-- You know, the human.
-- I think he moved to Tilwick.
#161430 - ferrand.d - Sun Aug 03, 2008 11:41 am
Thanks to all for your replies.
Quote: |
Rephrasing: Why do you even need a NON BLANK sleep function |
Quote: |
If it's SQLite, I can see where these functions might be used.
* ftruncate() is used for chopping off the end of a file that has become smaller without having to copy and rename. This might take place when a program runs VACUUM on a database to compact and repair it.
* fsync() is used to make sure that writes to a database or journal have actually taken effect on the storage medium (the D in ACID).
* I think SQLite might use sleep() for file locking: poll the file every second or so until it shows not locked or until a timeout expires. This is important for database files on a CIFS share, but libnds is most commonly used as a single-tasking operating environment incapable of mounting network shares, and a program on such a system might not need the locking. |
I need a sleep (and a ftruncate, and a fsync) function because SQLite needs it. But I don't need complex features like VACUUM or locking... so is there a way to disable this in SQLite ? If I understand well, I'll just need fsync ?
For the moment I tried to rewrite it like that (with Dwedit indications) :
Code: |
int fsync(int fd)
{
FILE* stream;
stream = fdopen(fd, "r");
fflush(stream);
return 0;
} |
It is dirty code, but it might work (like sleep())...
#161438 - Dwedit - Sun Aug 03, 2008 6:48 pm
I think this has to do with libfat not supporting posix style file IO instead of C standard library IO.
_________________
"We are merely sprites that dance at the beck and call of our button pressing overlord."
#161472 - ferrand.d - Mon Aug 04, 2008 6:27 pm
I've found a workaround for fsync().
I just added the flag O_SYNC to the open() function and now, all data should be written directly to the file without any buffer.
Have you got any ideas for the last function, ftruncate() ?
#161473 - Dwedit - Mon Aug 04, 2008 7:12 pm
There isn't any code in labfat anywhere to handle the truncate operation, there is only code to remove all the clusters from the chain and set the size to zero.
A truncate operation running on a FAT file system would follow the cluster chains, then break the cluster chain after a specified point, marking the remaining space as free, then change the file size from the file's directory entry. If it enlarged the file, it would instead need to append zeroes.
_________________
"We are merely sprites that dance at the beck and call of our button pressing overlord."
#161489 - zeruda - Mon Aug 04, 2008 10:30 pm
I don't know but maybe swidelay will be of use?
silent_code wrote: |
Your sleep function will only work for 60hz games, though it might be useful in some cases. :^) |
That's incorrect. When swiWaitforVBlank() returns it doesn't go back to the start of main(). It will continue on from where it left off. In the case given it returns at the for loop. It will go through another iteration which takes a few cycles and then it will hit swiWaitforVBlank() again. So it will be locked at 60 fps in the for loop, and once the loop ends the framerate will depend on whatever code is being called after that.
#161504 - silent_code - Tue Aug 05, 2008 8:03 am
I know that. Please read my other comments. :^)
Btw: Have you ever seen an NDS program go below 30 hz? I don't think that saying "the game loop get's locked at 60 hz" is correct, because it gets synchronised to the refresh rate, at a fraction of the latter (60, 30, 15 etc).
E.g., if you stall the graphics hardware, your game only runs at half speed.
My question was, if that would somehow have any influence on that sleep function implementation, but I guess it does not.
_________________
July 5th 08: "Volumetric Shadow Demo" 1.6.0 (final) source released
June 5th 08: "Zombie NDS" WIP released!
It's all on my page, just click WWW below.
#161506 - zeruda - Tue Aug 05, 2008 10:42 am
silent_code wrote: |
I don't think that saying "the game loop get's locked at 60 hz" is correct |
It's not the "game loop" that gets locked. It is the local for loop.
Code: |
unsigned sleep(unsigned int seconds)
{
int i, j;
for (i = 0; i < seconds; i++)
for (j = 0; j <60; j++)
swiWaitForVBlank();
return 0; |
So say you enter the loop with seconds = 10. i = 0 and j = 0. swiWaitForVBlank() is called so the hardware goes to sleep till VBlank. The VBlank does it's thing and returns to the loop which increments. j = 1. swiWaitForVBlank() again so goes to sleep. VBlank does it's thing(basically nothing) and returns. j = 2. VBlank and so on till j = 60. This means 60 VBlanks have been done and 1 second has passed. Goes to outer loop now i = 1 and then back to the inner loop j = 0. This continues for another 9 seconds.
What speed the rest of the game runs at is irrelevant since for 10 seconds none of it has been called at all. It has been stuck inside this sleep function inside the for loop.
#161508 - ferrand.d - Tue Aug 05, 2008 11:39 am
Sorry I'm french, so I don't really understand your debate ^^
Do you mean that my sleep() function works ? Or have I to rewrite it ?
#161513 - silent_code - Tue Aug 05, 2008 6:05 pm
@ zeruda: Oh, now I understand what you mean! Sorry for my ignorance of the inner loop. You are right. I guess I took the wording a bit too literally the other day... now that I think of it, it's something totally differnt from what I thought about (that was not about the sleep function implementation, let's not bloat the thread any further with it.) :?D
The function seems to be correct.
_________________
July 5th 08: "Volumetric Shadow Demo" 1.6.0 (final) source released
June 5th 08: "Zombie NDS" WIP released!
It's all on my page, just click WWW below.
#161516 - vuurrobin - Tue Aug 05, 2008 7:28 pm
Code: |
unsigned sleep(unsigned int seconds)
{
int i, j;
for (i = 0; i < seconds; i++)
for (j = 0; j <60; j++)
swiWaitForVBlank();
return 0; |
why would you use 2 for loops when 1 would be enough. if fact, I think that you could replace the entire function with a define:
Code: |
#define sleep(seconds) for(int i=0;i<((seconds)*60);i++){swiWaitForVBlank()} |
wouldn't this be easier?
#161518 - zeruda - Tue Aug 05, 2008 8:01 pm
ferrand.d wrote: |
Sorry I'm french, so I don't really understand your debate ^^
Do you mean that my sleep() function works ? Or have I to rewrite it ? |
Depends on the accuracy you need. Each frame on the DS is 1/60 of a second. So for example 10 seconds would be 600 frames. The first call to swiwaitforvblank in that loop however will be made part way through a frame, So the function will delay 599 complete frames and 1 partial frame. Or somewhere between 9.98333 seconds and 10.00 seconds. If that's enough accuracy then it'll work. If you need to be more precise maybe you can use swiDelay().
Quote: |
#define sleep(seconds) for(int i=0;i<((seconds)*60);i++){swiWaitForVBlank()}
wouldn't this be easier? |
Yes.
#161521 - Dwedit - Tue Aug 05, 2008 9:29 pm
Sleep is used as a way to synchronize processes in a multithreading system. Leave that function blank, because you don't have a multithreading system.
_________________
"We are merely sprites that dance at the beck and call of our button pressing overlord."
#161523 - ferrand.d - Tue Aug 05, 2008 10:40 pm
Okay. Thanks a lot for your advices about sleep().
I'm rewriting ftruncate() with the help of the libfat source code, I'll tell you if I have a problem ;)
#161536 - josath - Wed Aug 06, 2008 2:13 am
It seems to me ftruncate could be implemented simply like this:
Code: |
int ftruncate(int fd, int length) {
u8 byte;
lseek(fd, length, SEEK_SET);
read(fd, &byte, 1);
lseek(fd, length, SEEK_SET);
write(fd, &byte, 1);
}
|
If I'm correct in assuming writing to the middle of a file will truncate the file at that point.
#161538 - HyperHacker - Wed Aug 06, 2008 2:52 am
I just want to suggest you look over my ideas for a music player, especially with regards to the interface. LMP's one big annoyance for me is that it has that fancy bitmap interface that seems to take up a lot of CPU time to draw, and doesn't seem to be using interrupts to process input. So there are some songs that take up so much CPU power the buttons simply don't work because it never gets around to processing input.
Also, there are several places in my playlist where a song will start at the wrong sampling rate for a few seconds, and a couple where it will stay that way the entire time (with the buttons not responding). The workaround is to pause before the previous song ends, skip to the one after it, play, and skip back. Hopefully you can look into this.
LMP is one of the most useful homebrews out there :P glad to see someone working on it again.
_________________
I'm a PSP hacker now, but I still <3 DS.
#161570 - ferrand.d - Wed Aug 06, 2008 3:48 pm
josath wrote: |
It seems to me ftruncate could be implemented simply like this:
Code: |
int ftruncate(int fd, int length) {
u8 byte;
lseek(fd, length, SEEK_SET);
read(fd, &byte, 1);
lseek(fd, length, SEEK_SET);
write(fd, &byte, 1);
}
|
If I'm correct in assuming writing to the middle of a file will truncate the file at that point. |
Thanks for your code.
Correct me if i'm wrong, but if length is lower than the size of the file, this is not gonna truncate the file... In this case I thought I just had to write EOF where I want, but it seems a bit brutal... What do you think ?
@HyperHacker :
I read your suggestions, you have great ideas. I'll try to optimize LMP-ng but for the moment, I'm focusing on the menus of LMP-ng. (In fact, I spent a lot of time trying to understand the code, because it's difficult to continue a project when its code isn't commented ^^ and I haven't understood everything yet). But I'll optimize it later ;)
#161635 - ninjalj - Fri Aug 08, 2008 4:56 pm
ferrand.d wrote: |
Thanks for your code.
Correct me if i'm wrong, but if length is lower than the size of the file, this is not gonna truncate the file... In this case I thought I just had to write EOF where I want, but it seems a bit brutal... What do you think ?
|
That won't work. As someone said earlier, you have to follow the cluster chain on the FAT, free now unused clusters by setting it to 0 on the FAT, mark the current last cluster as last cluster on FAT (FFFF for FAT16 IIRC) and set the new file length on the dir entry.
#161637 - kusma - Fri Aug 08, 2008 6:22 pm
vuurrobin wrote: |
why would you use 2 for loops when 1 would be enough. if fact, I think that you could replace the entire function with a define:
|
Why not? It's easier to read the logic, and I don't see how you gain anything useful by removing a loop in this case.
vuurrobin wrote: |
Code: | #define sleep(seconds) for(int i=0;i<((seconds)*60);i++){swiWaitForVBlank()} |
wouldn't this be easier? |
No, using a macro is just type-unsafe (for the parameters) and generally trickier to debug. Using the preprocessor to implement function calls is just wrong in cases like this.
Your macro also has a defect. Try to compile the following code with your macro, and see how it fails (this works just fine when you use a function):
Code: |
if (true) sleep(10);
else printf("not sleeping");
|
It can be solved by wrapping the macro-"function" inside a "do{...}while(0)"-loop, though.
#162556 - ferrand.d - Thu Sep 04, 2008 9:40 pm
Hello everybody.
I had temporarily stopped the development of my version of LMP-ng during the rest of the holidays, because it was taking a lot of my time, but now that the school year has begun, I'd really like to finish it (at least, make it start on the DS without any error !), so I need your help.
I have done a lot of researches about FAT filesystem, clusters, I watched the code of libfat, etc... but I still can't find how to do, even with the procedure you gave me. Please help me with some code or anything...
Thanks very much for your help anyway !
#162557 - josath - Thu Sep 04, 2008 9:50 pm
ferrand.d wrote: |
Hello everybody.
I had temporarily stopped the development of my version of LMP-ng during the rest of the holidays, because it was taking a lot of my time, but now that the school year has begun, I'd really like to finish it |
huh...you're saying you have more free time during the school year, than during your holidays? :P