/** * \file * The selector implementations for the class interface. * * \author Georg Hopp * * \copyright * Copyright © 2014 Georg Hopp * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include #include #include #include "tr/class.h" #include "tr/interface/class.h" #include "tr/memory.h" /** * Create and initialize the structures for a new interface called * class. * Interfaces and Classes may have the same name because internally * everything that has to do with interfaces is prefixed with an i_ */ TR_CREATE_INTERFACE(TR_Class, 3); /* * SELECTOR DEFINITION * =================== */ /** * Selector for the ctor implementation. This one accepts a va_list. * * \cond PRIVATE */ void * TR_classNewv(TR_class_ptr class, va_list * params) { void * object = TR_calloc(1, class->object_size + sizeof(void*)); int ret; * (TR_class_ptr *)object = class; object += sizeof(void*); TR_RETCALL(object, TR_Class, ctor, ret, params); if (-1 == ret) { TR_classDelete(&object); } return object; } /** * Selector for the ctor implementation. This one accepts a variable * amount of arguments. */ void * TR_classNew(TR_class_ptr class, ...) { va_list params; void * object; va_start(params, class); object = TR_classNewv(class, ¶ms); va_end(params); return object; } /** * Selector for the dtor implementation. This one accepts a variable * amount of arguments. */ void TR_classDelete(void ** object) { if (NULL != *object) { void * mem; TR_CALL(*object, TR_Class, dtor); mem = *object - sizeof(void*); TR_MEM_FREE(mem); *object = NULL; } } /** * Selector for the clone implementation. This one accepts a variable * amount of arguments. */ void * TR_classClone(void * _object) { TR_class_ptr class = TR_GET_CLASS(_object); void * object = TR_calloc(1, class->object_size + sizeof(void*)); * (TR_class_ptr *)object = class; object += sizeof(void*); #undef clone TR_CALL(object, TR_Class, clone, _object); return object; } /** endcond */ /** * Interface caller function for i_class::ctor. * Call the constructor on an existing object identified by name. * In fact it calls first the destructor to ensure that all * possibly previously acquired resource are cleaned. */ int TR_objectInit(void * object, ...) { int ret; va_list params; va_start(params, object); TR_CALL(object, TR_Class, dtor); TR_RETCALL(object, TR_Class, ctor, ret, ¶ms); va_end(params); return ret; } // vim: set ts=4 sw=4: