@@ -110,11 +110,35 @@ uint8_t *z_priv_stack_find(k_thread_stack_t *stack)
110110#endif /* CONFIG_GEN_PRIV_STACKS */
111111
112112#ifdef CONFIG_DYNAMIC_OBJECTS
113+
114+ /*
115+ * Note that dyn_obj->data is where the kernel object resides
116+ * so it is the one that actually needs to be aligned.
117+ * Due to the need to get the the fields inside struct dyn_obj
118+ * from kernel object pointers (i.e. from data[]), the offset
119+ * from data[] needs to be fixed at build time. Therefore,
120+ * data[] is declared with __aligned(), such that when dyn_obj
121+ * is allocated with alignment, data[] is also aligned.
122+ * Due to this requirement, data[] needs to be aligned with
123+ * the maximum alignment needed for all kernel objects
124+ * (hence the following DYN_OBJ_DATA_ALIGN).
125+ */
126+ #ifdef ARCH_DYMANIC_OBJ_K_THREAD_ALIGNMENT
127+ #define DYN_OBJ_DATA_ALIGN_K_THREAD (ARCH_DYMANIC_OBJ_K_THREAD_ALIGNMENT)
128+ #else
129+ #define DYN_OBJ_DATA_ALIGN_K_THREAD (sizeof(void *))
130+ #endif
131+
132+ #define DYN_OBJ_DATA_ALIGN \
133+ MAX(DYN_OBJ_DATA_ALIGN_K_THREAD, (sizeof(void *)))
134+
113135struct dyn_obj {
114136 struct z_object kobj ;
115137 sys_dnode_t obj_list ;
116138 struct rbnode node ; /* must be immediately before data member */
117- uint8_t data []; /* The object itself */
139+
140+ /* The object itself */
141+ uint8_t data [] __aligned (DYN_OBJ_DATA_ALIGN_K_THREAD );
118142};
119143
120144extern struct z_object * z_object_gperf_find (const void * obj );
@@ -156,6 +180,26 @@ static size_t obj_size_get(enum k_objects otype)
156180 return ret ;
157181}
158182
183+ static size_t obj_align_get (enum k_objects otype )
184+ {
185+ size_t ret ;
186+
187+ switch (otype ) {
188+ case K_OBJ_THREAD :
189+ #ifdef ARCH_DYMANIC_OBJ_K_THREAD_ALIGNMENT
190+ ret = ARCH_DYMANIC_OBJ_K_THREAD_ALIGNMENT ;
191+ #else
192+ ret = sizeof (void * );
193+ #endif
194+ break ;
195+ default :
196+ ret = sizeof (void * );
197+ break ;
198+ }
199+
200+ return ret ;
201+ }
202+
159203static bool node_lessthan (struct rbnode * a , struct rbnode * b )
160204{
161205 return a < b ;
@@ -166,6 +210,13 @@ static inline struct dyn_obj *node_to_dyn_obj(struct rbnode *node)
166210 return CONTAINER_OF (node , struct dyn_obj , node );
167211}
168212
213+ static inline struct rbnode * dyn_obj_to_node (void * obj )
214+ {
215+ struct dyn_obj * dobj = CONTAINER_OF (obj , struct dyn_obj , data );
216+
217+ return & dobj -> node ;
218+ }
219+
169220static struct dyn_obj * dyn_object_find (void * obj )
170221{
171222 struct rbnode * node ;
@@ -176,7 +227,7 @@ static struct dyn_obj *dyn_object_find(void *obj)
176227 * so just a little arithmetic is necessary to locate the
177228 * corresponding struct rbnode
178229 */
179- node = ( struct rbnode * )(( char * ) obj - sizeof ( struct rbnode ) );
230+ node = dyn_obj_to_node ( obj );
180231
181232 k_spinlock_key_t key = k_spin_lock (& lists_lock );
182233 if (rb_contains (& obj_rb_tree , node )) {
@@ -252,11 +303,11 @@ static void thread_idx_free(uintptr_t tidx)
252303 sys_bitfield_set_bit ((mem_addr_t )_thread_idx_map , tidx );
253304}
254305
255- struct z_object * z_dynamic_object_create ( size_t size )
306+ struct z_object * z_dynamic_object_aligned_create ( size_t align , size_t size )
256307{
257308 struct dyn_obj * dyn ;
258309
259- dyn = z_thread_malloc ( sizeof (* dyn ) + size );
310+ dyn = z_thread_aligned_alloc ( align , sizeof (* dyn ) + size );
260311 if (dyn == NULL ) {
261312 LOG_ERR ("could not allocate kernel object, out of memory" );
262313 return NULL ;
@@ -288,13 +339,6 @@ void *z_impl_k_object_alloc(enum k_objects otype)
288339
289340 switch (otype ) {
290341 case K_OBJ_THREAD :
291- /* aligned allocator required for X86 and X86_64 */
292- if (IS_ENABLED (CONFIG_X86 ) || IS_ENABLED (CONFIG_X86_64 )) {
293- LOG_ERR ("object type '%s' forbidden on x86 and x86_64" ,
294- otype_to_str (otype ));
295- return NULL ;
296- }
297-
298342 if (!thread_idx_alloc (& tidx )) {
299343 LOG_ERR ("out of free thread indexes" );
300344 return NULL ;
@@ -313,7 +357,8 @@ void *z_impl_k_object_alloc(enum k_objects otype)
313357 break ;
314358 }
315359
316- zo = z_dynamic_object_create (obj_size_get (otype ));
360+ zo = z_dynamic_object_aligned_create (obj_align_get (otype ),
361+ obj_size_get (otype ));
317362 if (zo == NULL ) {
318363 return NULL ;
319364 }
0 commit comments