Allegro.cc - Online Community

Allegro.cc Forums » Allegro Development » al_fprintf

This thread is locked; no one can reply to it. rss feed Print
al_fprintf
DanielH
Member #934
January 2001
avatar

I was looking at this post. This lead me to the Allegro development road map. I thought I would contribute one of the "Nice To Have" section.

// header file
#ifndef __al_included_allegro5_alprintf_h
#define __al_included_allegro5_alprintf_h

#include <allegro5\allegro.h>
#include <stdarg.h>

bool al_vfprintf(ALLEGRO_FILE *pfile, const char *format, va_list args);
bool al_fprintf(ALLEGRO_FILE *pfile, const char *format, ...);

#endif // __al_included_allegro5_alprintf_h

#SelectExpand
1// source file 2#include "al_fprintf.h" 3 4bool al_vfprintf(ALLEGRO_FILE *pfile, const char *format, va_list args) 5{ 6 bool rv = false; 7 ALLEGRO_USTR *ustr = 0; 8 size_t size = 0; 9 10 if (pfile != 0 && format != 0) 11 { 12 ustr = al_ustr_dup(al_ustr_empty_string()); 13 14 if (ustr) 15 { 16 rv = al_ustr_vappendf(ustr, format, args); 17 18 if (rv) 19 { 20 size = al_ustr_size(ustr); 21 22 if (size > 0) 23 { 24 if (size != al_fwrite(pfile, (const void*)(al_cstr(ustr)), size)) 25 { 26 rv = false; 27 } 28 } 29 } 30 31 al_ustr_free(ustr); 32 } 33 } 34 35 return rv; 36} 37 38bool al_fprintf(ALLEGRO_FILE *pfile, const char *format, ...) 39{ 40 bool rv = false; 41 va_list args = 0; 42 43 if (pfile != 0 && format != 0) 44 { 45 va_start(args, format); 46 rv = al_vfprintf(pfile, format, args); 47 va_end(args); 48 } 49 50 return rv; 51}

Chris Katko
Member #1,881
January 2002
avatar

You beat me to it by actually doing work, you monster!

-----sig:
“Programs should be written for people to read, and only incidentally for machines to execute.” - Structure and Interpretation of Computer Programs

Trent Gamblin
Member #261
April 2000
avatar

Is there any reason you have two functions instead of just one?

Thomas Fjellstrom
Member #476
June 2000
avatar

The first one should probably be called al_vfprintf rather than al_fprintf. Not least of which because c doesn't let you overload functions.

--
Thomas Fjellstrom - [website] - [email] - [Allegro Wiki] - [Allegro TODO]
"If you can't think of a better solution, don't try to make a better solution." -- weapon_S
"The less evidence we have for what we believe is certain, the more violently we defend beliefs against those who don't agree" -- https://twitter.com/neiltyson/status/592870205409353730

DanielH
Member #934
January 2001
avatar

Trent Been working with ALLEGRO_USTR alot lately and since it has two appendf functions (... & va_args). Just copying the same style.

Thomas fixed

Trent Gamblin
Member #261
April 2000
avatar

I think this is a useful addition for someone to add. Will try to remember to do it myself.

Thomas Fjellstrom
Member #476
June 2000
avatar

I agree. This is definitely useful. Between supporting format printing to files, it also uses the ustr code to make sure UTF8 writing works.

--
Thomas Fjellstrom - [website] - [email] - [Allegro Wiki] - [Allegro TODO]
"If you can't think of a better solution, don't try to make a better solution." -- weapon_S
"The less evidence we have for what we believe is certain, the more violently we defend beliefs against those who don't agree" -- https://twitter.com/neiltyson/status/592870205409353730

Edgar Reynaldo
Member #8,592
May 2007
avatar

Thomas Fjellstrom
Member #476
June 2000
avatar

Can you test this code a bit? hammer it a little with invalid input and the like? Once validated, I can apply.

--
Thomas Fjellstrom - [website] - [email] - [Allegro Wiki] - [Allegro TODO]
"If you can't think of a better solution, don't try to make a better solution." -- weapon_S
"The less evidence we have for what we believe is certain, the more violently we defend beliefs against those who don't agree" -- https://twitter.com/neiltyson/status/592870205409353730

DanielH
Member #934
January 2001
avatar

Edgar Fixed

Thomas If someone else could tackle this. I don't quite have the time for a while.

tobing
Member #5,213
November 2004
avatar

I have put the code into aintern_file, and will test it a bit. Instead of returning a bool I would prefer to return an int, indicating the number of bytes written...

DanielH
Member #934
January 2001
avatar

tobing I had it return bool because of the use of ustr's appendf function. Of course I agree it should return the size written to file.

I haven't used plain C in forever. Does it support size_t?

// header file
#ifndef __al_included_allegro5_alprintf_h
#define __al_included_allegro5_alprintf_h

#include <allegro5\allegro.h>
#include <stdarg.h>

size_t al_vfprintf(ALLEGRO_FILE *pfile, const char *format, va_list args);
size_t al_fprintf(ALLEGRO_FILE *pfile, const char *format, ...);

#endif // __al_included_allegro5_alprintf_h

#SelectExpand
1// source file 2#include "al_fprintf.h" 3 4size_t al_vfprintf(ALLEGRO_FILE *pfile, const char *format, va_list args) 5{ 6 size_t rv = 0; 7 ALLEGRO_USTR *ustr = 0; 8 9 if (pfile != 0 && format != 0) 10 { 11 ustr = al_ustr_dup(al_ustr_empty_string()); 12 13 if (ustr) 14 { 15 if (al_ustr_vappendf(ustr, format, args)) 16 { 17 rv = al_ustr_size(ustr); 18 19 if (rv > 0) 20 { 21 rv = al_fwrite(pfile, (const void*)(al_cstr(ustr)), rv); 22 } 23 } 24 25 al_ustr_free(ustr); 26 } 27 } 28 29 return rv; 30} 31 32size_t al_fprintf(ALLEGRO_FILE *pfile, const char *format, ...) 33{ 34 size_t rv = 0; 35 va_list args = 0; 36 37 if (pfile != 0 && format != 0) 38 { 39 va_start(args, format); 40 rv = al_vfprintf(pfile, format, args); 41 va_end(args); 42 } 43 44 return rv; 45}

On a side note:

al_ustr_dup(al_ustr_empty_string());
v.s.
al_ustr_new("");

P.S. at work so can't actually run and test the code I just changed

Thomas Fjellstrom
Member #476
June 2000
avatar

size_t is valid in C as well, and most functions, especially newer ones will use size_t over int. size_t may even be 64bit on a 64bit platform.

--
Thomas Fjellstrom - [website] - [email] - [Allegro Wiki] - [Allegro TODO]
"If you can't think of a better solution, don't try to make a better solution." -- weapon_S
"The less evidence we have for what we believe is certain, the more violently we defend beliefs against those who don't agree" -- https://twitter.com/neiltyson/status/592870205409353730

tobing
Member #5,213
November 2004
avatar

Here's a patch for current origin/5.1 in git, that contains the last implementation by DanielH, but with al_ustr_new("") instead of the dup on empty string.

I have tested this a bit, and works fine with unicode characters.

Trent Gamblin
Member #261
April 2000
avatar

This is committed. I added some quick documentation.

Also changed it to return a negative number on error like stdio fprintf.

tobing
Member #5,213
November 2004
avatar

Thanks for submitting and doing the cleanup. ;)

The return is a size_t, so returning -1 is not exactly doing what it should do, so maybe we should return int instead of size_t?

Arthur Kalliokoski
Second in Command
February 2005
avatar

The libc fprintf returns the number of bytes in an int, so I'd vote for that. Someday 2147483648 bytes in a single write won't be enough, but today is not that day.

“Throughout history, poverty is the normal condition of man. Advances which permit this norm to be exceeded — here and there, now and then — are the work of an extremely small minority, frequently despised, often condemned, and almost always opposed by all right-thinking people. Whenever this tiny minority is kept from creating, or (as sometimes happens) is driven out of a society, the people then slip back into abject poverty. This is known as "bad luck.”

― Robert A. Heinlein

Trent Gamblin
Member #261
April 2000
avatar

tobing said:

The return is a size_t, so returning -1 is not exactly doing what it should do, so maybe we should return int instead of size_t?

Good catch, thanks. Changing it to int.

DanielH
Member #934
January 2001
avatar

Thanks guys.

However, can someone answer a previous question?

al_ustr_dup(al_ustr_empty_string());

v.s.

al_ustr_new("");

I see that my code was changed for the latter case. In looking at other's code, I've seen both.

tobing
Member #5,213
November 2004
avatar

Ah, I didn't realize that this was a question.

Well, I used the second variant because the result seems to be the same, but uses only one call.

DanielH
Member #934
January 2001
avatar

You're right. I did post it, but didn't phrase it as a question.

Edgar Reynaldo
Member #8,592
May 2007
avatar

Small patch to fix a warning about comparison between signed and unsigned integers (I hate seeing warnings) :

#SelectExpand
1 src/file.c | 2 +- 2 1 file changed, 1 insertion(+), 1 deletion(-) 3 4diff --git a/src/file.c b/src/file.c 5index 16f1e80..b6b2ce6 100644 6--- a/src/file.c 7+++ b/src/file.c 8@@ -559,7 +559,7 @@ int al_vfprintf(ALLEGRO_FILE *pfile, const char *format, va_list args) 9 if (size > 0) 10 { 11 rv = al_fwrite(pfile, (const void*)(al_cstr(ustr)), size); 12- if (rv != size) { 13+ if (rv != (int)size) { 14 rv = -1; 15 } 16 }

Trent Gamblin
Member #261
April 2000
avatar

Committed.

tobing
Member #5,213
November 2004
avatar

Go to: