Robert Shearman : widl: Support correlation descriptors in structures.

Alexandre Julliard julliard at wine.codeweavers.com
Tue Jan 24 06:45:15 CST 2006


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

Author: Robert Shearman <rob at codeweavers.com>
Date:   Tue Jan 24 11:12:54 2006 +0100

widl: Support correlation descriptors in structures.

---

 tools/widl/typegen.c |  152 ++++++++++++++++++++++++++++++--------------------
 1 files changed, 92 insertions(+), 60 deletions(-)

diff --git a/tools/widl/typegen.c b/tools/widl/typegen.c
index 2a395c9..8f12934 100644
--- a/tools/widl/typegen.c
+++ b/tools/widl/typegen.c
@@ -43,6 +43,9 @@
 #include "typegen.h"
 
 static const func_t *current_func;
+static const var_t *current_fields;
+
+static size_t type_memsize(const type_t *t, int ptr_level, const expr_t *array);
 
 static int print_file(FILE *file, int indent, const char *format, ...)
 {
@@ -215,8 +218,7 @@ void write_procformatstring(FILE *file, 
 }
 
 /* write conformance / variance descriptor */
-/* FIXME: only works for top-level variables at the moment */
-static size_t write_conf_or_var_desc(FILE *file, const func_t *func, const expr_t *expr)
+static size_t write_conf_or_var_desc(FILE *file, const func_t *func, const var_t *fields, const expr_t *expr)
 {
     unsigned char operator_type = 0;
     const char *operator_string = "no operators";
@@ -269,80 +271,104 @@ static size_t write_conf_or_var_desc(FIL
 
     if (subexpr->type == EXPR_IDENTIFIER)
     {
-        if (func)
+        unsigned char correlation_type;
+        const type_t *correlation_variable = NULL;
+        unsigned char param_type = 0;
+        const char *param_type_string = NULL;
+        size_t offset;
+
+        if (fields)
+        {
+            const var_t *var;
+
+            for (offset = 0, var = fields; var; var = NEXT_LINK(var))
+            {
+                offset -= type_memsize(var->type, var->ptr_level, var->array);
+                if (!strcmp(var->name, subexpr->u.sval))
+                {
+                    correlation_variable = var->type;
+                    break;
+                }
+            }
+            if (!correlation_variable)
+                error("write_conf_or_var_desc: couldn't find variable %s in structure\n",
+                      subexpr->u.sval);
+
+            correlation_type = RPC_FC_NORMAL_CONFORMANCE;
+        }
+        else
         {
-            size_t stack_offset;
             const var_t *var = func->args;
-            unsigned char param_type = 0;
-            const char *param_type_string = NULL;
-            const type_t *conformance_type = NULL;
 
             while (NEXT_LINK(var)) var = NEXT_LINK(var);
-            for (stack_offset = 0; var; stack_offset += sizeof(void *), var = PREV_LINK(var))
+            /* FIXME: not all stack variables are sizeof(void *) */
+            for (offset = 0; var; offset += sizeof(void *), var = PREV_LINK(var))
             {
                 if (!strcmp(var->name, subexpr->u.sval))
                 {
-                    conformance_type = var->type;
+                    correlation_variable = var->type;
                     break;
                 }
             }
-            if (!conformance_type)
-                error("write_conf_or_var_desc: couldn't find variable %s\n",
+            if (!correlation_variable)
+                error("write_conf_or_var_desc: couldn't find variable %s in function\n",
                     subexpr->u.sval);
 
-            while (type_has_ref(conformance_type))
-                conformance_type = conformance_type->ref;
+            correlation_type = RPC_FC_TOP_LEVEL_CONFORMANCE;
+        }
 
-            switch (conformance_type->type)
-            {
-            case RPC_FC_CHAR:
-            case RPC_FC_SMALL:
-                param_type = RPC_FC_SMALL;
-                param_type_string = "FC_SMALL";
-                break;
-            case RPC_FC_BYTE:
-            case RPC_FC_USMALL:
-                param_type = RPC_FC_USMALL;
-                param_type_string = "FC_USMALL";
-                break;
-            case RPC_FC_WCHAR:
-            case RPC_FC_SHORT:
-                param_type = RPC_FC_SHORT;
-                param_type_string = "FC_SHORT";
-                break;
-            case RPC_FC_USHORT:
-                param_type = RPC_FC_USHORT;
-                param_type_string = "FC_USHORT";
-                break;
-            case RPC_FC_LONG:
-                param_type = RPC_FC_LONG;
-                param_type_string = "FC_LONG";
-                break;
-            case RPC_FC_ULONG:
-                param_type = RPC_FC_ULONG;
-                param_type_string = "FC_ULONG";
-                break;
-            default:
-                error("write_conf_or_var_desc: conformance variable type not supported 0x%x\n",
-                    conformance_type->type);
-            }
+        while (type_has_ref(correlation_variable))
+            correlation_variable = correlation_variable->ref;
 
-            print_file(file, 2, "0x%x, /* Corr desc: parameter, %s */\n",
-                    RPC_FC_TOP_LEVEL_CONFORMANCE | param_type,
-                    param_type_string);
-            print_file(file, 2, "0x%x, /* %s */\n", operator_type, operator_string);
-            print_file(file, 2, "0x%x, /* x86 stack size / offset = %d */\n", stack_offset, stack_offset);
+        switch (correlation_variable->type)
+        {
+        case RPC_FC_CHAR:
+        case RPC_FC_SMALL:
+            param_type = RPC_FC_SMALL;
+            param_type_string = "FC_SMALL";
+            break;
+        case RPC_FC_BYTE:
+        case RPC_FC_USMALL:
+            param_type = RPC_FC_USMALL;
+            param_type_string = "FC_USMALL";
+            break;
+        case RPC_FC_WCHAR:
+        case RPC_FC_SHORT:
+            param_type = RPC_FC_SHORT;
+            param_type_string = "FC_SHORT";
+            break;
+        case RPC_FC_USHORT:
+            param_type = RPC_FC_USHORT;
+            param_type_string = "FC_USHORT";
+            break;
+        case RPC_FC_LONG:
+            param_type = RPC_FC_LONG;
+            param_type_string = "FC_LONG";
+            break;
+        case RPC_FC_ULONG:
+            param_type = RPC_FC_ULONG;
+            param_type_string = "FC_ULONG";
+            break;
+        default:
+            error("write_conf_or_var_desc: conformance variable type not supported 0x%x\n",
+                correlation_variable->type);
         }
-        else
-            error("write_conf_or_var_desc: not supported for non-functions yet\n");
+
+        print_file(file, 2, "0x%x, /* Corr desc: %s%s */\n",
+                correlation_type | param_type,
+                correlation_type == RPC_FC_TOP_LEVEL_CONFORMANCE ? "parameter, " : "",
+                param_type_string);
+        print_file(file, 2, "0x%x, /* %s */\n", operator_type, operator_string);
+        print_file(file, 2, "0x%x, /* %soffset = %d */\n",
+                   offset,
+                   correlation_type == RPC_FC_TOP_LEVEL_CONFORMANCE ? "x86 stack size / " : "",
+                   offset);
     }
     else
         error("write_conf_or_var_desc: expression type %d\n", subexpr->type);
     return 4;
 }
 
-static size_t type_memsize(const type_t *t, int ptr_level, const expr_t *array);
-
 static size_t fields_memsize(const var_t *v)
 {
     size_t size = 0;
@@ -454,7 +480,7 @@ static size_t write_string_tfs(FILE *fil
         print_file(file, 2, "0x%x, /* FC_STRING_SIZED */\n", RPC_FC_STRING_SIZED);
         typestring_size = 2;
 
-        typestring_size += write_conf_or_var_desc(file, current_func, size_is);
+        typestring_size += write_conf_or_var_desc(file, current_func, NULL, size_is);
 
         return typestring_size;
     }
@@ -557,7 +583,9 @@ static size_t write_array_tfs(FILE *file
             print_file(file, 2, "NdrFcShort(0x%x), /* %d */\n", element_size, element_size);
             typestring_size += 2;
 
-            typestring_size += write_conf_or_var_desc(file, current_func, length_is);
+            typestring_size += write_conf_or_var_desc(file, current_func,
+                                                      current_fields,
+                                                      length_is);
 
             /* FIXME: write out pointer descriptor if necessary */
 
@@ -580,7 +608,8 @@ static size_t write_array_tfs(FILE *file
             print_file(file, 2, "NdrFcShort(0x%x), /* %d */\n", element_size, element_size);
             typestring_size = 4;
 
-            typestring_size += write_conf_or_var_desc(file, current_func, size_is);
+            typestring_size += write_conf_or_var_desc(file, current_func,
+                                                      current_fields, size_is);
 
             /* FIXME: write out pointer descriptor if necessary */
 
@@ -603,8 +632,11 @@ static size_t write_array_tfs(FILE *file
             print_file(file, 2, "NdrFcShort(0x%x), /* %d */\n", element_size, element_size);
             typestring_size = 4;
 
-            typestring_size += write_conf_or_var_desc(file, current_func, size_is);
-            typestring_size += write_conf_or_var_desc(file, current_func, length_is);
+            typestring_size += write_conf_or_var_desc(file, current_func,
+                                                      current_fields, size_is);
+            typestring_size += write_conf_or_var_desc(file, current_func,
+                                                      current_fields,
+                                                      length_is);
 
             /* FIXME: write out pointer descriptor if necessary */
 




More information about the wine-cvs mailing list