blob: 4a716e35805e7a6bf3baaaaac53541325c46f84d [file] [log] [blame]
// Licensed to the Apache Software Foundation (ASF) under one
// or more contributor license agreements. See the NOTICE file
// distributed with this work for additional information
// regarding copyright ownership. The ASF licenses this file
// to you under the Apache License, Version 2.0 (the
// "License"); you may not use this file except in compliance
// with the License. You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing,
// software distributed under the License is distributed on an
// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
// KIND, either express or implied. See the License for the
// specific language governing permissions and limitations
// under the License.
#include "DFPlatform.h"
#include <DocFormats/DFError.h>
#include "DFCommon.h"
#include <assert.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
struct DFError {
size_t retainCount;
char *message;
};
void DFErrorSetPosix(DFError **error, int code)
{
DFErrorFormat(error,"%s",strerror(code));
}
void DFErrorVFormat(DFError **error, const char *format, va_list ap)
{
if (error == NULL) {
return;
}
va_list ap2;
va_copy(ap2,ap);
size_t nchars = vsnprintf(NULL,0,format,ap2);
va_end(ap2);
char *message = (char *)xmalloc(nchars+1);
va_copy(ap2,ap);
vsnprintf(message,nchars+1,format,ap2);
va_end(ap2);
if (*error != NULL) {
// Error object exists; replace the existing message
free((*error)->message);
(*error)->message = message;
}
else {
// Error object does not exist; create a new one
(*error) = (DFError *)xcalloc(1,sizeof(DFError));
(*error)->retainCount = 1;
(*error)->message = message;
}
}
void DFErrorFormat(DFError **error, const char *format, ...)
{
va_list ap;
va_start(ap,format);
DFErrorVFormat(error,format,ap);
va_end(ap);
}
DFError *DFErrorRetain(DFError *error)
{
if (error == NULL)
return NULL;
error->retainCount++;
return error;
}
void DFErrorRelease(DFError *error)
{
if (error == NULL)
return;
assert(error->retainCount > 0);
error->retainCount--;
if (error->retainCount == 0) {
free(error->message);
free(error);
}
}
const char *DFErrorMessage(DFError **error)
{
if ((error == NULL) || (*error == NULL))
return "Unknown error";
else
return (*error)->message;
}