Mercurial > pub > dyncall > dyncall
diff dyncallback/dyncall_callback_x64.c @ 546:ba70fb631bea
x64:
* support for non-standard aggr-by-value packing (#pragma pack, etc.)
* callbacks: handling callconv prefixes in signature
author | Tassilo Philipp |
---|---|
date | Tue, 31 May 2022 19:29:34 +0200 |
parents | 71c884e610f0 |
children |
line wrap: on
line diff
--- a/dyncallback/dyncall_callback_x64.c Tue May 31 18:35:06 2022 +0200 +++ b/dyncallback/dyncall_callback_x64.c Tue May 31 19:29:34 2022 +0200 @@ -48,6 +48,7 @@ void dcbInitCallback2(DCCallback* pcb, const DCsigchar* signature, DCCallbackHandler* handler, void* userdata, DCaggr *const * aggrs) { const DCsigchar *ch = signature; + int mode = DC_CALL_C_DEFAULT; DCint num_aggrs = 0; pcb->handler = handler; @@ -55,6 +56,12 @@ pcb->aggrs = NULL; pcb->aggr_return_register = -2; /* default, = no aggr as ret value */ + if(*ch == DC_SIGCHAR_CC_PREFIX) + { + mode = dcGetModeFromCCSigChar(ch[1]); + ch += 2; + } + while(*ch) num_aggrs += (*(ch++) == DC_SIGCHAR_AGGREGATE); @@ -68,7 +75,9 @@ #if defined(DC_UNIX) if (!ag || (ag->sysv_classes[0] == SYSVC_MEMORY)) { #else - if (!ag || ag->size > 8) { + if (mode == DC_CALL_C_DEFAULT_THIS) { + pcb->aggr_return_register = 1; + } else if (!ag || ag->size > 8 || /*not a power of 2?*/(ag->size & (ag->size - 1))) { #endif /* we need to "return" this aggr as a hidden pointer (first arg) */ pcb->aggr_return_register = 0;