add attr_returns_allocated for functions that allocate new objects

This commit is contained in:
Andrei Alexeyev 2019-08-04 01:29:41 +03:00
parent f0dc4ec04a
commit 10d3e4226b
No known key found for this signature in database
GPG key ID: 363707CD4C7FE8A4
12 changed files with 32 additions and 29 deletions

View file

@ -86,6 +86,6 @@ bool color_equals(const Color *clr, const Color *clr2)
attr_nonnull(1, 2);
char* color_str(const Color *clr)
attr_nonnull(1) attr_returns_nonnull attr_nodiscard;
attr_nonnull(1) attr_returns_allocated;
#endif // IGUARD_color_h

View file

@ -61,7 +61,7 @@ typedef struct Dialog {
} Dialog;
Dialog *dialog_create(void)
attr_returns_nonnull attr_nodiscard;
attr_returns_allocated;
void dialog_set_actor(Dialog *d, DialogSide side, DialogActor *actor)
attr_nonnull(1);

View file

@ -390,7 +390,7 @@ HT_DECLARE_FUNC(void, destroy, (HT_BASETYPE *ht))
*
* Returns the allocated hashtable structure.
*/
INLINE attr_returns_nonnull attr_nodiscard
INLINE attr_returns_allocated
HT_DECLARE_FUNC(HT_BASETYPE*, new, (void)) {
HT_BASETYPE *ht = calloc(1, sizeof(HT_BASETYPE));
HT_FUNC(create)(ht);

View file

@ -92,7 +92,7 @@ void* alist_foreach(ListAnchor *list, ListAnchorForeachCallback callback, void *
void* alist_callback_free_element(ListAnchor *list, List *elem, void *arg);
void alist_free_all(ListAnchor *list) attr_nonnull(1);
ListContainer* list_wrap_container(void *data) attr_nodiscard;
ListContainer* list_wrap_container(void *data) attr_returns_allocated;
// type-generic macros

View file

@ -37,9 +37,9 @@ struct ObjectPoolStats {
#define OBJPOOL_ALLOC(typename,max_objects) objpool_alloc(sizeof(typename), max_objects, #typename)
#define OBJPOOL_ACQUIRE(pool, type) CASTPTR_ASSUME_ALIGNED(objpool_acquire(pool), type)
ObjectPool *objpool_alloc(size_t obj_size, size_t max_objects, const char *tag) attr_returns_nonnull attr_nodiscard attr_nonnull(3);
ObjectPool *objpool_alloc(size_t obj_size, size_t max_objects, const char *tag) attr_returns_allocated attr_nonnull(3);
void objpool_free(ObjectPool *pool) attr_nonnull(1);
void *objpool_acquire(ObjectPool *pool) attr_returns_max_aligned attr_returns_nonnull attr_nodiscard attr_hot attr_nonnull(1);
void *objpool_acquire(ObjectPool *pool) attr_returns_allocated attr_hot attr_nonnull(1);
void objpool_release(ObjectPool *pool, void *object) attr_hot attr_nonnull(1, 2);
void objpool_get_stats(ObjectPool *pool, ObjectPoolStats *stats) attr_nonnull(1, 2);
size_t objpool_object_size(ObjectPool *pool) attr_nonnull(1);

View file

@ -77,7 +77,7 @@ typedef struct TaskParams {
* On failure, returns NULL.
*/
TaskManager* taskmgr_create(uint numthreads, SDL_ThreadPriority prio, const char *name)
attr_nodiscard attr_nonnull(3);
attr_nodiscard attr_returns_max_aligned attr_nonnull(3);
/**
* Submit a new task to [mgr] described by [params]. It is generally placed at the end of the
@ -94,7 +94,7 @@ TaskManager* taskmgr_create(uint numthreads, SDL_ThreadPriority prio, const char
* On failure, returns NULL.
*/
Task* taskmgr_submit(TaskManager *mgr, TaskParams params)
attr_nonnull(1) attr_nodiscard;
attr_nonnull(1) attr_nodiscard attr_returns_max_aligned;
/**
* Returns the number of remaining tasks in [mgr]'s queue.

View file

@ -249,6 +249,10 @@ typedef complex max_align_t;
#define attr_returns_max_aligned \
attr_returns_aligned(alignof(max_align_t))
// Shorthand: always returns non-null pointer aligned to max_align_t; no discard.
#define attr_returns_allocated \
attr_returns_nonnull attr_returns_max_aligned attr_nodiscard
// Structure must not be initialized with an implicit (non-designated) initializer.
#if __has_attribute(designated_init) && defined(TAISEI_BUILDCONF_USE_DESIGNATED_INIT)
#define attr_designated_init \

View file

@ -13,8 +13,8 @@
#include <SDL.h>
void* memdup(const void *src, size_t size);
void inherit_missing_pointers(uint num, void *dest[num], void *const base[num]);
void* memdup(const void *src, size_t size) attr_returns_allocated attr_nonnull(1);
void inherit_missing_pointers(uint num, void *dest[num], void *const base[num]) attr_nonnull(2, 3);
bool is_main_thread(void);
INLINE uint32_t float_to_bits(float f) {

View file

@ -142,9 +142,9 @@ typedef struct Pixmap {
PixmapOrigin origin;
} Pixmap;
void* pixmap_alloc_buffer(PixmapFormat format, size_t width, size_t height) attr_nodiscard;
void* pixmap_alloc_buffer_for_copy(const Pixmap *src) attr_nonnull(1) attr_nodiscard;
void* pixmap_alloc_buffer_for_conversion(const Pixmap *src, PixmapFormat format) attr_nonnull(1) attr_nodiscard;
void* pixmap_alloc_buffer(PixmapFormat format, size_t width, size_t height) attr_returns_allocated;
void* pixmap_alloc_buffer_for_copy(const Pixmap *src) attr_nonnull(1) attr_returns_allocated;
void* pixmap_alloc_buffer_for_conversion(const Pixmap *src, PixmapFormat format) attr_nonnull(1) attr_returns_allocated;
void pixmap_copy(const Pixmap *src, Pixmap *dst) attr_nonnull(1, 2);
void pixmap_copy_alloc(const Pixmap *src, Pixmap *dst) attr_nonnull(1, 2);
@ -168,6 +168,6 @@ bool pixmap_load_stream(SDL_RWops *stream, Pixmap *dst) attr_nonnull(1, 2) attr_
bool pixmap_load_stream_tga(SDL_RWops *stream, Pixmap *dst) attr_nonnull(1, 2) attr_nodiscard;
bool pixmap_check_filename(const char *path);
char* pixmap_source_path(const char *prefix, const char *path);
char* pixmap_source_path(const char *prefix, const char *path) attr_nodiscard;
#endif // IGUARD_util_pixmap_h

View file

@ -15,7 +15,7 @@
typedef struct SHA256State SHA256State;
SHA256State* sha256_new(void) attr_nodiscard;
SHA256State* sha256_new(void) attr_returns_allocated;
void sha256_update(SHA256State *state, const uint8_t *data, size_t len) attr_nonnull(1, 2);
void sha256_final(SHA256State *state, uint8_t hash[SHA256_BLOCK_SIZE], size_t hashlen) attr_nonnull(1, 2);
void sha256_free(SHA256State *state);

View file

@ -29,10 +29,9 @@
#undef strdup
#define strdup _ts_strdup
INLINE attr_returns_max_aligned attr_nonnull(1) char *strdup(const char *str) {
char *s = malloc(strlen(str) + 1);
strcpy(s, str);
return s;
INLINE attr_returns_allocated attr_nonnull(1) char *strdup(const char *str) {
size_t sz = strlen(str) + 1;
return memcpy(malloc(sz), str, sz);
}
#undef strtok_r
@ -47,23 +46,23 @@ bool strstartswith(const char *s, const char *p) attr_pure;
bool strendswith_any(const char *s, const char **earray) attr_pure;
bool strstartswith_any(const char *s, const char **earray) attr_pure;
void stralloc(char **dest, const char *src);
char* strjoin(const char *first, ...) attr_sentinel;
char* vstrfmt(const char *fmt, va_list args);
char* strfmt(const char *fmt, ...) attr_printf(1, 2);
char* strjoin(const char *first, ...) attr_sentinel attr_returns_allocated;
char* vstrfmt(const char *fmt, va_list args) attr_returns_allocated;
char* strfmt(const char *fmt, ...) attr_printf(1, 2) attr_returns_allocated;
void strip_trailing_slashes(char *buf);
char* strtok_r(char *str, const char *delim, char **nextp);
char* strappend(char **dst, char *src);
char* strftimealloc(const char *fmt, const struct tm *timeinfo);
char* strftimealloc(const char *fmt, const struct tm *timeinfo) attr_returns_allocated;
void expand_escape_sequences(char *str);
uint32_t* ucs4chr(const uint32_t *ucs4, uint32_t chr);
size_t ucs4len(const uint32_t *ucs4);
void utf8_to_ucs4(const char *utf8, size_t bufsize, uint32_t buf[bufsize]) attr_nonnull(1, 3);
uint32_t* utf8_to_ucs4_alloc(const char *utf8) attr_nonnull(1) attr_returns_nonnull attr_nodiscard;
uint32_t* utf8_to_ucs4_alloc(const char *utf8) attr_nonnull(1) attr_returns_allocated attr_nonnull(1);
void ucs4_to_utf8(const uint32_t *ucs4, size_t bufsize, char buf[bufsize]) attr_nonnull(1, 3);
char* ucs4_to_utf8_alloc(const uint32_t *ucs4) attr_nonnull(1) attr_returns_nonnull attr_nodiscard;
char* ucs4_to_utf8_alloc(const uint32_t *ucs4) attr_nonnull(1) attr_returns_allocated attr_nonnull(1);
uint32_t utf8_getch(const char **src) attr_nonnull(1);

View file

@ -58,16 +58,16 @@ VFSNode* vfs_locate(VFSNode *root, const char *path) attr_nonnull(1, 2) attr_nod
// Light wrappers around the virtual functions, safe to call even on nodes that
// don't implement the corresponding method. "free" is not included, there should
// be no reason to call it. It wouldn't do what you'd expect anyway; use vfs_decref.
char* vfs_node_repr(VFSNode *node, bool try_syspath) attr_nonnull(1);
VFSInfo vfs_node_query(VFSNode *node) attr_nonnull(1) attr_nodiscard;
char* vfs_node_syspath(VFSNode *node) attr_nonnull(1) attr_nodiscard;
char* vfs_node_repr(VFSNode *node, bool try_syspath) attr_returns_allocated attr_nonnull(1);
VFSInfo vfs_node_query(VFSNode *node) attr_nonnull(1) attr_nodiscard attr_nonnull(1);
char* vfs_node_syspath(VFSNode *node) attr_nonnull(1) attr_returns_max_aligned attr_nodiscard attr_nonnull(1);
bool vfs_node_mount(VFSNode *mountroot, const char *subname, VFSNode *mountee) attr_nonnull(1, 3);
bool vfs_node_unmount(VFSNode *mountroot, const char *subname) attr_nonnull(1);
VFSNode* vfs_node_locate(VFSNode *root, const char *path) attr_nonnull(1, 2) attr_nodiscard;
const char* vfs_node_iter(VFSNode *node, void **opaque) attr_nonnull(1);
void vfs_node_iter_stop(VFSNode *node, void **opaque) attr_nonnull(1);
bool vfs_node_mkdir(VFSNode *parent, const char *subdir) attr_nonnull(1);
SDL_RWops* vfs_node_open(VFSNode *filenode, VFSOpenMode mode) attr_nonnull(1);
SDL_RWops* vfs_node_open(VFSNode *filenode, VFSOpenMode mode) attr_nonnull(1) attr_nodiscard;
void vfs_hook_on_shutdown(VFSShutdownHandler, void *arg);
void vfs_print_tree_recurse(SDL_RWops *dest, VFSNode *root, char *prefix, const char *name) attr_nonnull(1, 2, 3, 4);