1 /* Common operations. 2 3 Copyright (C) 2015-2018, 2021 Paul Boddie <paul@boddie.org.uk> 4 5 This program is free software; you can redistribute it and/or modify it under 6 the terms of the GNU General Public License as published by the Free Software 7 Foundation; either version 3 of the License, or (at your option) any later 8 version. 9 10 This program is distributed in the hope that it will be useful, but WITHOUT 11 ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS 12 FOR A PARTICULAR PURPOSE. See the GNU General Public License for more 13 details. 14 15 You should have received a copy of the GNU General Public License along with 16 this program. If not, see <http://www.gnu.org/licenses/>. 17 */ 18 19 #ifndef __OPS_H__ 20 #define __OPS_H__ 21 22 #include "types.h" 23 #include <string.h> /* for __COPY */ 24 25 /* Get object reference from attribute. */ 26 27 __ref __VALUE(__attr attr); 28 29 /* Direct access and manipulation of static objects. */ 30 31 __attr __load_static_ignore(__ref obj); 32 __attr __load_static_replace(__attr context, __ref obj); 33 __attr __load_static_test(__attr context, __ref obj); 34 35 /* Direct retrieval operations, returning attributes. */ 36 37 __attr __load_via_class__(__ref obj, int pos); 38 __attr __load_via_object__(__ref obj, int pos); 39 __attr __get_class_and_load__(__ref obj, int pos); 40 41 #define __load_via_class(OBJ, ATTRNAME) (__load_via_class__(OBJ, __ATTRPOS(ATTRNAME))) 42 #define __load_via_object(OBJ, ATTRNAME) (__load_via_object__(OBJ, __ATTRPOS(ATTRNAME))) 43 #define __get_class_and_load(OBJ, ATTRNAME) (__get_class_and_load__(OBJ, __ATTRPOS(ATTRNAME))) 44 45 /* Direct storage operations. */ 46 47 void __store_target(__attr *target, __attr value); 48 int __store_via_class__(__ref obj, int pos, __attr value); 49 int __store_via_object__(__ref obj, int pos, __attr value); 50 int __store_via_object_internal__(__ref obj, int pos, __attr value); 51 int __get_class_and_store__(__ref obj, int pos, __attr value); 52 53 #define __store_via_class(OBJ, ATTRNAME, VALUE) (__store_via_class__(OBJ, __ATTRPOS(ATTRNAME), VALUE)) 54 #define __store_via_object(OBJ, ATTRNAME, VALUE) (__store_via_object__(OBJ, __ATTRPOS(ATTRNAME), VALUE)) 55 #define __store_via_object_internal(OBJ, ATTRNAME, VALUE) (__store_via_object_internal__(OBJ, __ATTRPOS(ATTRNAME), VALUE)) 56 #define __get_class_and_store(OBJ, ATTRNAME, VALUE) (__get_class_and_store__(OBJ, __ATTRPOS(ATTRNAME), VALUE)) 57 58 /* Introspection. */ 59 60 int __is_instance(__ref obj); 61 int __is_subclass(__ref obj, __attr cls); 62 int __is_instance_subclass(__ref obj, __attr cls); 63 int __is_type_instance(__ref obj); 64 __ref __get_class(__ref obj); 65 __attr __get_class_attr(__ref obj); 66 67 /* Attribute testing operations. */ 68 69 __ref __test_specific_instance(__ref obj, __ref type); 70 __ref __test_specific_object(__ref obj, __ref type); 71 __ref __test_specific_type(__ref obj, __ref type); 72 73 __ref __test_common_instance__(__ref obj, int pos, int code); 74 __ref __test_common_object__(__ref obj, int pos, int code); 75 __ref __test_common_type__(__ref obj, int pos, int code); 76 77 #define __to_error(REF) (REF ? REF : (__raise_type_error(), (__ref) 0)) 78 79 #define __test_common_instance(OBJ, TYPENAME) (__test_common_instance__(OBJ, __ATTRPOS(TYPENAME), __ATTRCODE(TYPENAME))) 80 #define __test_common_object(OBJ, TYPENAME) (__test_common_object__(OBJ, __ATTRPOS(TYPENAME), __ATTRCODE(TYPENAME))) 81 #define __test_common_type(OBJ, TYPENAME) (__test_common_type__(OBJ, __ATTRPOS(TYPENAME), __ATTRCODE(TYPENAME))) 82 83 /* Attribute testing and retrieval operations. */ 84 85 __attr __check_and_load_via_object_null(__ref obj, int pos, int code); 86 87 __attr __check_and_load_via_class__(__ref obj, int pos, int code); 88 __attr __check_and_load_via_object__(__ref obj, int pos, int code); 89 __attr __check_and_load_via_any__(__ref obj, int pos, int code); 90 91 #define __check_and_load_via_class(OBJ, ATTRNAME) (__check_and_load_via_class__(OBJ, __ATTRPOS(ATTRNAME), __ATTRCODE(ATTRNAME))) 92 #define __check_and_load_via_object(OBJ, ATTRNAME) (__check_and_load_via_object__(OBJ, __ATTRPOS(ATTRNAME), __ATTRCODE(ATTRNAME))) 93 #define __check_and_load_via_any(OBJ, ATTRNAME) (__check_and_load_via_any__(OBJ, __ATTRPOS(ATTRNAME), __ATTRCODE(ATTRNAME))) 94 95 /* Attribute testing and storage operations. */ 96 97 int __check_and_store_via_class__(__ref obj, int pos, int code, __attr value); 98 int __check_and_store_via_object__(__ref obj, int pos, int code, __attr value); 99 int __check_and_store_via_object_internal__(__ref obj, int pos, int code, __attr value); 100 int __check_and_store_via_any__(__ref obj, int pos, int code, __attr value); 101 102 #define __check_and_store_via_class(OBJ, ATTRNAME, VALUE) (__check_and_store_via_class__(OBJ, __ATTRPOS(ATTRNAME), __ATTRCODE(ATTRNAME), VALUE)) 103 #define __check_and_store_via_object(OBJ, ATTRNAME, VALUE) (__check_and_store_via_object__(OBJ, __ATTRPOS(ATTRNAME), __ATTRCODE(ATTRNAME), VALUE)) 104 #define __check_and_store_via_object_internal(OBJ, ATTRNAME, VALUE) (__check_and_store_via_object_internal__(OBJ, __ATTRPOS(ATTRNAME), __ATTRCODE(ATTRNAME), VALUE)) 105 #define __check_and_store_via_any(OBJ, ATTRNAME, VALUE) (__check_and_store_via_any__(OBJ, __ATTRPOS(ATTRNAME), __ATTRCODE(ATTRNAME), VALUE)) 106 107 /* Context-related operations. */ 108 109 int __test_context_update(__attr context, __attr attr, int invoke); 110 __attr __test_context(__attr context, __attr attr); 111 __attr __update_context(__attr context, __attr attr); 112 __attr __test_context_revert(int target, __attr context, __attr attr, __attr contexts[]); 113 __attr __test_context_static(int target, __attr context, __ref value, __attr contexts[]); 114 115 #define __get_accessor(__TARGET) (__tmp_values[__TARGET]) 116 #define __get_context(__TARGET) (__tmp_contexts[__TARGET]) 117 #define __set_context(__TARGET, __ATTR) (__tmp_contexts[__TARGET] = (__ATTR)) 118 #define __set_private_context(__ATTR) (__tmp_private_context = (__ATTR)) 119 #define __set_accessor(__TARGET, __ATTR) (__tmp_values[__TARGET] = (__ATTR)) 120 #define __set_target_accessor(__ATTR) (__tmp_target_value = (__ATTR)) 121 122 /* Context testing for invocations. */ 123 124 __attr __unwrap_callable(__attr callable); 125 __attr (*__get_function_unchecked(__attr target))(); 126 __attr (*__get_function(__attr context, __attr target))(); 127 __attr (*__get_function_unwrapped(__attr context, __attr target))(); 128 __attr (*__get_function_member(__attr target))(); 129 __attr (*__check_and_get_function(__attr context, __attr target))(); 130 __attr (*__check_and_get_function_unwrapped(__attr context, __attr target))(); 131 132 /* Parameter position operations. */ 133 134 int __HASPARAM(const __ptable *ptable, int ppos, int pcode); 135 136 /* Conversions. */ 137 138 __attr __CONTEXT_AS_VALUE(__attr attr); 139 140 /* Type testing. */ 141 142 __ref __ISFUNC(__ref obj); 143 144 #define __ISNULL(__ATTR) (!(__ATTR.rawvalue & (~__TAG_MASK))) 145 146 /* Attribute codes and positions for type objects. */ 147 148 unsigned int __TYPECODE(__ref obj); 149 unsigned int __TYPEPOS(__ref obj); 150 151 /* Memory allocation. */ 152 153 void *__ALLOCATE(size_t nmemb, size_t size); 154 void *__ALLOCATEIM(size_t nmemb, size_t size); 155 void *__REALLOCATE(void *ptr, size_t size); 156 157 /* Copying of structures. */ 158 159 __ref __COPY(__ref obj, size_t size); 160 void __COPY_TO(__ref source, __ref target, size_t size); 161 162 /* Stack management. */ 163 164 extern _Thread_local __attr __stack; 165 166 #define __STACK_SECTION_SIZE 4096 167 168 __attr __stack_init(); 169 __attr __stack_allocate(__attr __stack, size_t size); 170 void __stack_expand(__attr __stack); 171 void __stack_contract(__attr __stack, char *level); 172 173 /* Stack access. */ 174 175 __attr __load(__attr value); 176 __attr __store_local(__attr target, __attr value); 177 __attr __return(__attr result, __section *section, char *level); 178 179 #endif /* __OPS_H__ */