summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorJérémy Zurcher <jeremy@asynk.ch>2013-12-30 15:24:15 +0100
committerJérémy Zurcher <jeremy@asynk.ch>2014-01-03 16:22:21 +0100
commit77bd3ce6c678066164126251f93f2053ea599aea (patch)
tree7771401c8b158361dbff521b0e4e1f302d1d0673
parent0bb069a31dce42ccc50be23a0b98340371c94243 (diff)
eo2: call stack grows and shrinks
-rw-r--r--src/lib/eo/eo.c70
1 files changed, 56 insertions, 14 deletions
diff --git a/src/lib/eo/eo.c b/src/lib/eo/eo.c
index ca9eee8b48..86a648e3ea 100644
--- a/src/lib/eo/eo.c
+++ b/src/lib/eo/eo.c
@@ -268,9 +268,9 @@ _eo_kls_itr_func_get(const _Eo_Class *cur_klass, Eo_Op op)
268EAPI Eo2_Hook_Call eo2_hook_call_pre = NULL; 268EAPI Eo2_Hook_Call eo2_hook_call_pre = NULL;
269EAPI Eo2_Hook_Call eo2_hook_call_post = NULL; 269EAPI Eo2_Hook_Call eo2_hook_call_post = NULL;
270 270
271// FIXME: per thread stack, grow/shrink 271// FIXME: Thread Local Storage
272#define EO2_INVALID_DATA (void *) -1 272#define EO2_INVALID_DATA (void *) -1
273#define EO2_CALL_STACK_DEPTH 100 273#define EO2_CALL_STACK_DEPTH 30
274 274
275typedef struct _Eo2_Stack_Frame 275typedef struct _Eo2_Stack_Frame
276{ 276{
@@ -286,9 +286,11 @@ typedef struct _Eo2_Stack_Frame
286typedef struct _Eo2_Call_Stack { 286typedef struct _Eo2_Call_Stack {
287 Eo2_Stack_Frame *stack; 287 Eo2_Stack_Frame *stack;
288 Eo2_Stack_Frame *frame_ptr; 288 Eo2_Stack_Frame *frame_ptr;
289 Eo2_Stack_Frame *last_frame;
290 Eo2_Stack_Frame *shrink_frame;
289} Eo2_Call_Stack; 291} Eo2_Call_Stack;
290 292
291static Eo2_Call_Stack eo2_call_stack = { NULL, NULL }; 293static Eo2_Call_Stack eo2_call_stack = { NULL, NULL, NULL, NULL };
292 294
293static Eina_Bool 295static Eina_Bool
294_eo2_call_stack_init() 296_eo2_call_stack_init()
@@ -298,7 +300,9 @@ _eo2_call_stack_init()
298 return EINA_FALSE; 300 return EINA_FALSE;
299 301
300 // first frame is never used 302 // first frame is never used
301 eo2_call_stack.frame_ptr = &eo2_call_stack.stack[0]; 303 eo2_call_stack.frame_ptr = eo2_call_stack.stack;
304 eo2_call_stack.last_frame = &eo2_call_stack.stack[EO2_CALL_STACK_DEPTH - 1];
305 eo2_call_stack.shrink_frame = eo2_call_stack.stack;
302 306
303 return EINA_TRUE; 307 return EINA_TRUE;
304} 308}
@@ -310,6 +314,40 @@ _eo2_call_stack_free()
310 free(eo2_call_stack.stack); 314 free(eo2_call_stack.stack);
311} 315}
312 316
317
318static inline void
319_eo2_call_stack_resize(Eina_Bool grow)
320{
321 size_t sz, next_sz;
322 int frame_offset;
323
324 frame_offset = eo2_call_stack.frame_ptr - eo2_call_stack.stack;
325 sz = eo2_call_stack.last_frame - eo2_call_stack.stack + 1;
326 if (grow)
327 next_sz = sz << 1;
328 else
329 next_sz = sz >> 1;
330
331 DBG("resize from %lu to %lu", sz, next_sz);
332 eo2_call_stack.stack = realloc(eo2_call_stack.stack, next_sz * sizeof(Eo2_Stack_Frame));
333 if(!eo2_call_stack.stack)
334 {
335 CRI("unable to resize call stack, abort.");
336 abort();
337 }
338
339 eo2_call_stack.frame_ptr = &eo2_call_stack.stack[frame_offset];
340 eo2_call_stack.last_frame = &eo2_call_stack.stack[next_sz - 1];
341
342 if (grow)
343 frame_offset = (sz >> 1);
344 if (next_sz == EO2_CALL_STACK_DEPTH)
345 frame_offset = 0;
346 else
347 frame_offset = (next_sz >> 1);
348 eo2_call_stack.shrink_frame = &eo2_call_stack.stack[frame_offset];
349}
350
313static inline Eina_Bool 351static inline Eina_Bool
314_eo2_do_internal(const Eo *eo_id, const Eo_Class *cur_klass_id, 352_eo2_do_internal(const Eo *eo_id, const Eo_Class *cur_klass_id,
315 Eina_Bool is_super, Eo2_Stack_Frame *fptr, Eo2_Stack_Frame *pfptr) 353 Eina_Bool is_super, Eo2_Stack_Frame *fptr, Eo2_Stack_Frame *pfptr)
@@ -345,18 +383,16 @@ _eo2_do_start(const Eo *eo_id, const Eo_Class *cur_klass_id, Eina_Bool is_super,
345{ 383{
346 Eo2_Stack_Frame *fptr, *pfptr; 384 Eo2_Stack_Frame *fptr, *pfptr;
347 385
386 if (eo2_call_stack.frame_ptr == eo2_call_stack.last_frame)
387 _eo2_call_stack_resize(EINA_TRUE);
388
348 fptr = eo2_call_stack.frame_ptr; 389 fptr = eo2_call_stack.frame_ptr;
349 if (((fptr - eo2_call_stack.stack) + 1) >= EO2_CALL_STACK_DEPTH)
350 {
351 ERR("eo2 call stack overflow !!!");
352 return EINA_FALSE;
353 }
354 390
355 pfptr = ((eo_id) && (fptr->eo_id == eo_id) ? fptr : NULL); 391 pfptr = ((eo_id) && (fptr->eo_id == eo_id) ? fptr : NULL);
356 fptr++; 392 fptr++;
357 393
358 if (!_eo2_do_internal(eo_id, cur_klass_id, is_super, fptr, pfptr)) 394 if (!_eo2_do_internal(eo_id, cur_klass_id, is_super, fptr, pfptr))
359 return EINA_FALSE; 395 return EINA_FALSE;
360 396
361 if(_eo_is_a_class(eo_id)) 397 if(_eo_is_a_class(eo_id))
362 { 398 {
@@ -388,10 +424,16 @@ _eo2_do_end(const Eo **eo_id EINA_UNUSED)
388 memset(fptr, 0, sizeof (Eo2_Stack_Frame)); 424 memset(fptr, 0, sizeof (Eo2_Stack_Frame));
389 fptr->obj_data = EO2_INVALID_DATA; 425 fptr->obj_data = EO2_INVALID_DATA;
390 426
391 if (fptr == &eo2_call_stack.stack[0]) 427 if (fptr == eo2_call_stack.stack)
392 ERR("eo2 call stack underflow !!!"); 428 {
393 else 429 CRI("call stack underflow, abort.");
394 eo2_call_stack.frame_ptr--; 430 abort();
431 }
432
433 eo2_call_stack.frame_ptr--;
434
435 if (fptr == eo2_call_stack.shrink_frame)
436 _eo2_call_stack_resize(EINA_FALSE);
395} 437}
396 438
397EAPI Eina_Bool 439EAPI Eina_Bool