Eric Pouech : dbghelp: First stab at supporting calling convention in function signature.

Alexandre Julliard julliard at wine.codeweavers.com
Mon Dec 19 14:22:14 CST 2005


Module: wine
Branch: refs/heads/master
Commit: be849decf60eb49811995f9129d72808424b8d12
URL:    http://source.winehq.org/git/?p=wine.git;a=commit;h=be849decf60eb49811995f9129d72808424b8d12

Author: Eric Pouech <eric.pouech at wanadoo.fr>
Date:   Mon Dec 19 18:22:54 2005 +0100

dbghelp: First stab at supporting calling convention in function signature.

---

 dlls/dbghelp/dbghelp_private.h |    4 +++-
 dlls/dbghelp/dwarf.c           |   23 ++++++++++++++++++++++-
 dlls/dbghelp/msc.c             |   17 +++++++++++------
 dlls/dbghelp/stabs.c           |    8 ++++----
 dlls/dbghelp/type.c            |   18 ++++++++++++++++--
 5 files changed, 56 insertions(+), 14 deletions(-)

diff --git a/dlls/dbghelp/dbghelp_private.h b/dlls/dbghelp/dbghelp_private.h
index 1291162..8d8cb70 100644
--- a/dlls/dbghelp/dbghelp_private.h
+++ b/dlls/dbghelp/dbghelp_private.h
@@ -220,6 +220,7 @@ struct symt_function_signature
     struct symt                 symt;
     struct symt*                rettype;
     struct vector               vchildren;
+    enum CV_call_e              call_conv;
 };
 
 struct symt_function_arg_type
@@ -472,7 +473,8 @@ extern struct symt_array*
                                    struct symt* base);
 extern struct symt_function_signature*
                     symt_new_function_signature(struct module* module, 
-                                                struct symt* ret_type);
+                                                struct symt* ret_type,
+                                                enum CV_call_e call_conv);
 extern BOOL         symt_add_function_signature_parameter(struct module* module,
                                                           struct symt_function_signature* sig,
                                                           struct symt* param);
diff --git a/dlls/dbghelp/dwarf.c b/dlls/dbghelp/dwarf.c
index f16dd63..946852e 100644
--- a/dlls/dbghelp/dwarf.c
+++ b/dlls/dbghelp/dwarf.c
@@ -443,6 +443,17 @@ typedef enum dwarf_operation_e {
   DW_OP_nop = 0x96
 } dwarf_operation_t;
 
+enum dwarf_calling_convention
+{
+    DW_CC_normal = 0x1,
+    DW_CC_program = 0x2,
+    DW_CC_nocall = 0x3
+};
+
+#define DW_CC_lo_user 0x40
+#define DW_CC_hi_user 0xff
+
+
 /**
  * Parsers
  */
@@ -1876,6 +1887,8 @@ static struct symt_function* dwarf2_pars
   unsigned char decl_line = 0;
   dwarf2_abbrev_entry_attr_t* attr = NULL;
   unsigned long next_sibling = 0;
+  enum CV_call_e call_conv = CV_CALL_FAR_C; /* FIXME: assuming C source code */
+  unsigned cc;
 
   TRACE("%s, for %lu\n", dwarf2_debug_ctx(ctx), entry->entry_code); 
 
@@ -1908,6 +1921,14 @@ static struct symt_function* dwarf2_pars
     case DW_AT_inline:
       inl_flags = dwarf2_parse_byte(ctx);
       break;
+    case DW_AT_calling_convention:
+        switch (cc = dwarf2_parse_byte(ctx))
+        {
+        case DW_CC_normal: break;
+        case DW_CC_nocall: call_conv = -1;
+        default: FIXME("Unsupported calling convention %d\n", cc);
+        }
+        break;
     /* not work yet, need parsing .debug_line and using Compil Unit stmt_list
     case DW_AT_decl_file:
       decl_file =  dwarf2_parse_byte(ctx);
@@ -1921,7 +1942,7 @@ static struct symt_function* dwarf2_pars
       dwarf2_parse_attr(attr, ctx);
     }
   }
-  sig_type = symt_new_function_signature(module, ret_type);
+  sig_type = symt_new_function_signature(module, ret_type, call_conv);
   if (!is_decl) {
     func_type = symt_new_function(module, compiland, name, addr, size, &sig_type->symt);
     if (low_pc && high_pc) {
diff --git a/dlls/dbghelp/msc.c b/dlls/dbghelp/msc.c
index 054f27b..93f0474 100644
--- a/dlls/dbghelp/msc.c
+++ b/dlls/dbghelp/msc.c
@@ -726,11 +726,12 @@ static int codeview_add_type_struct(stru
 }
 
 static int codeview_new_func_signature(struct module* module, unsigned typeno,
-                                           unsigned ret_type)
+                                       unsigned ret_type, enum CV_call_e call_conv)
 {
     struct symt* symt;
     symt = &symt_new_function_signature(module, 
-                                        codeview_get_type(ret_type, FALSE))->symt;
+                                        codeview_get_type(ret_type, FALSE),
+                                        call_conv)->symt;
     return codeview_add_type(typeno, symt);
 }
 
@@ -916,25 +917,29 @@ static int codeview_parse_type_table(str
             break;
         case LF_PROCEDURE_V1:
             retv = codeview_new_func_signature(module, curr_type, 
-                                               type->procedure_v1.rvtype);
+                                               type->procedure_v1.rvtype,
+                                               type->procedure_v1.call);
             break;
         case LF_PROCEDURE_V2:
             retv = codeview_new_func_signature(module, curr_type, 
-                                               type->procedure_v2.rvtype);
+                                               type->procedure_v2.rvtype,
+                                               type->procedure_v2.call);
             break;
         case LF_MFUNCTION_V1:
             /* FIXME: for C++, this is plain wrong, but as we don't use arg types
              * nor class information, this would just do for now
              */
             retv = codeview_new_func_signature(module, curr_type,
-                                               type->mfunction_v1.rvtype);
+                                               type->mfunction_v1.rvtype,
+                                               type->mfunction_v1.call);
             break;
         case LF_MFUNCTION_V2:
             /* FIXME: for C++, this is plain wrong, but as we don't use arg types
              * nor class information, this would just do for now
              */
             retv = codeview_new_func_signature(module, curr_type,
-                                               type->mfunction_v2.rvtype);
+                                               type->mfunction_v2.rvtype,
+                                               type->mfunction_v2.call);
             break;
         case LF_ARGLIST_V1:
         case LF_ARGLIST_V2:
diff --git a/dlls/dbghelp/stabs.c b/dlls/dbghelp/stabs.c
index f29f552..76629b7 100644
--- a/dlls/dbghelp/stabs.c
+++ b/dlls/dbghelp/stabs.c
@@ -848,7 +848,7 @@ static int stabs_pts_read_type_def(struc
 	    break;
 	case 'f':
 	    PTS_ABORTIF(ptd, stabs_pts_read_type_def(ptd, NULL, &ref_dt) == -1);
-	    new_dt = &symt_new_function_signature(ptd->module, ref_dt)->symt;
+	    new_dt = &symt_new_function_signature(ptd->module, ref_dt, -1)->symt;
 	    break;
 	case 'e':
 	    new_dt = &symt_new_enum(ptd->module, typename)->symt;
@@ -930,7 +930,7 @@ static int stabs_pts_read_type_def(struc
             {
                 ptd->ptr++;
                 PTS_ABORTIF(ptd, stabs_pts_read_type_def(ptd, NULL, &ref_dt) == -1);
-                new_dt = &symt_new_function_signature(ptd->module, ref_dt)->symt;
+                new_dt = &symt_new_function_signature(ptd->module, ref_dt, -1)->symt;
             }
             else
             {
@@ -940,7 +940,7 @@ static int stabs_pts_read_type_def(struc
                 PTS_ABORTIF(ptd, stabs_pts_read_type_def(ptd, NULL, &cls_dt) == -1);
                 PTS_ABORTIF(ptd, *ptd->ptr++ != ',');
                 PTS_ABORTIF(ptd, stabs_pts_read_type_def(ptd, NULL, &ref_dt) == -1);
-                new_dt = &symt_new_function_signature(ptd->module, ref_dt)->symt;
+                new_dt = &symt_new_function_signature(ptd->module, ref_dt, -1)->symt;
                 while (*ptd->ptr == ',')
                 {
                     ptd->ptr++;
@@ -1422,7 +1422,7 @@ BOOL stabs_parse(struct module* module, 
                                                 (load_offset + stab_ptr->n_value - curr_func->address) : 0);
                 }
                 func_type = symt_new_function_signature(module, 
-                                                        stabs_parse_type(ptr));
+                                                        stabs_parse_type(ptr), -1);
                 curr_func = symt_new_function(module, compiland, symname, 
                                               load_offset + stab_ptr->n_value, 0,
                                               &func_type->symt);
diff --git a/dlls/dbghelp/type.c b/dlls/dbghelp/type.c
index fba6942..a62d50a 100644
--- a/dlls/dbghelp/type.c
+++ b/dlls/dbghelp/type.c
@@ -298,7 +298,8 @@ struct symt_array* symt_new_array(struct
 }
 
 struct symt_function_signature* symt_new_function_signature(struct module* module, 
-                                                            struct symt* ret_type)
+                                                            struct symt* ret_type,
+                                                            enum CV_call_e call_conv)
 {
     struct symt_function_signature*     sym;
 
@@ -307,6 +308,7 @@ struct symt_function_signature* symt_new
         sym->symt.tag = SymTagFunctionType;
         sym->rettype  = ret_type;
         vector_init(&sym->vchildren, sizeof(struct symt*), 4);
+        sym->call_conv = call_conv;
         symt_add_type(module, &sym->symt);
     }
     return sym;
@@ -735,11 +737,20 @@ BOOL symt_get_info(const struct symt* ty
         X(VARIANT) = ((const struct symt_data*)type)->u.value;
         break;
 
+    case TI_GET_CALLING_CONVENTION:
+        if (type->tag != SymTagFunctionType) return FALSE;
+        if (((const struct symt_function_signature*)type)->call_conv == -1)
+        {
+            FIXME("No support for calling convention for this signature\n");
+            X(DWORD) = CV_CALL_FAR_C; /* FIXME */
+        }
+        else X(DWORD) = ((const struct symt_function_signature*)type)->call_conv;
+        break;
+
 #undef X
 
     case TI_GET_ADDRESSOFFSET:
     case TI_GET_ARRAYINDEXTYPEID:
-    case TI_GET_CALLING_CONVENTION:
     case TI_GET_CLASSPARENTID:
     case TI_GET_SYMINDEX:
     case TI_GET_THISADJUST:
@@ -749,6 +760,9 @@ BOOL symt_get_info(const struct symt* ty
     case TI_IS_EQUIV_TO:
         FIXME("Unsupported GetInfo request (%u)\n", req);
         return FALSE;
+    default:
+        FIXME("Unknown GetInfo request (%u)\n", req);
+        return FALSE;
     }
 
     return TRUE;




More information about the wine-cvs mailing list