Welcome to mirror list, hosted at ThFree Co, Russian Federation.

git.blender.org/blender.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorBrecht Van Lommel <brechtvanlommel@pandora.be>2009-06-20 18:53:30 +0400
committerBrecht Van Lommel <brechtvanlommel@pandora.be>2009-06-20 18:53:30 +0400
commit980dab90282ab3ca63ac44b174344a6607934fb9 (patch)
tree709898d45bf36de91c7ad528f3d9f7375c820536 /source/blender/blenlib/intern/BLI_dynstr.c
parented2887f7209a31ff7bb52147e0baf330477f7548 (diff)
2.5: fix for crash in BLI_dynstr_appendf, each vsnprintf call
apparently needs its own va_start/va_end.
Diffstat (limited to 'source/blender/blenlib/intern/BLI_dynstr.c')
-rw-r--r--source/blender/blenlib/intern/BLI_dynstr.c52
1 files changed, 48 insertions, 4 deletions
diff --git a/source/blender/blenlib/intern/BLI_dynstr.c b/source/blender/blenlib/intern/BLI_dynstr.c
index 04388ea946f..dd10d898a7f 100644
--- a/source/blender/blenlib/intern/BLI_dynstr.c
+++ b/source/blender/blenlib/intern/BLI_dynstr.c
@@ -92,7 +92,7 @@ void BLI_dynstr_vappendf(DynStr *ds, const char *format, va_list args)
if(len == sizeof(fixedmessage))
message= fixedmessage;
else
- message= MEM_callocN(sizeof(char)*len+1, "BLI_dynstr_appendf");
+ message= MEM_callocN(sizeof(char)*(len+1), "BLI_dynstr_appendf");
retval= vsnprintf(message, len, format, args);
@@ -132,10 +132,54 @@ void BLI_dynstr_vappendf(DynStr *ds, const char *format, va_list args)
void BLI_dynstr_appendf(DynStr *ds, const char *format, ...)
{
va_list args;
+ char *message, fixedmessage[256];
+ int len= 256, maxlen= 65536, retval;
+
+ /* note that it's tempting to just call BLI_dynstr_vappendf here
+ * and avoid code duplication, that crashes on some system because
+ * va_start/va_end have to be called for each vsnprintf call */
- va_start(args, format);
- BLI_dynstr_vappendf(ds, format, args);
- va_end(args);
+ while(1) {
+ if(len == sizeof(fixedmessage))
+ message= fixedmessage;
+ else
+ message= MEM_callocN(sizeof(char)*(len+1), "BLI_dynstr_appendf");
+
+ va_start(args, format);
+ retval= vsnprintf(message, len, format, args);
+ va_end(args);
+
+ if(retval == -1) {
+ /* -1 means not enough space, but on windows it may also mean
+ * there is a formatting error, so we impose a maximum length */
+ if(message != fixedmessage)
+ MEM_freeN(message);
+ message= NULL;
+
+ len *= 2;
+ if(len > maxlen) {
+ fprintf(stderr, "BLI_dynstr_append text too long or format error.\n");
+ break;
+ }
+ }
+ else if(retval > len) {
+ /* in C99 the actual length required is returned */
+ if(message != fixedmessage)
+ MEM_freeN(message);
+ message= NULL;
+
+ len= retval;
+ }
+ else
+ break;
+ }
+
+ if(message) {
+ BLI_dynstr_append(ds, message);
+
+ if(message != fixedmessage)
+ MEM_freeN(message);
+ }
}
int BLI_dynstr_get_len(DynStr *ds) {