WIDL: generate some marshalling code for stubs
Mike McCormack
mike at codeweavers.com
Wed Sep 8 03:35:27 CDT 2004
ChangeLog:
* generate some marshalling code for stubs
-------------- next part --------------
Index: tools/widl/proxy.c
===================================================================
RCS file: /home/wine/wine/tools/widl/proxy.c,v
retrieving revision 1.11
diff -u -r1.11 proxy.c
--- tools/widl/proxy.c 6 Sep 2004 20:25:39 -0000 1.11
+++ tools/widl/proxy.c 8 Sep 2004 07:04:41 -0000
@@ -54,6 +54,13 @@
return r;
}
+static type_t *get_base_type( type_t *type )
+{
+ while( type->ref )
+ type = type->ref;
+ return type;
+}
+
static void write_stubdescproto(void)
{
print_proxy( "extern const MIDL_STUB_DESC Object_StubDesc;\n");
@@ -93,6 +100,33 @@
print_proxy( "\n");
}
+static void write_formatstring( int proc )
+{
+ const char *t, *n;
+ if( !proc )
+ {
+ t = "TYPE";
+ n = "Type";
+ }
+ else
+ {
+ t = "PROC";
+ n = "Proc";
+ }
+ print_proxy( "static const MIDL_%s_FORMAT_STRING __MIDL_%sFormatString =\n", t, n);
+ print_proxy( "{\n");
+ indent++;
+ print_proxy( "0,\n");
+ print_proxy( "{\n");
+ indent++;
+ print_proxy( "0\n");
+ indent--;
+ print_proxy( "}\n");
+ indent--;
+ print_proxy( "};\n");
+ print_proxy( "\n");
+}
+
static void init_proxy(void)
{
if (proxy) return;
@@ -100,7 +134,7 @@
print_proxy( "/*** Autogenerated by WIDL %s - Do not edit ***/\n", WIDL_FULLVERSION);
print_proxy( "\n");
print_proxy( "#ifndef __REDQ_RPCPROXY_H_VERSION__\n");
- print_proxy( "#define __REDQ_RPCPROXY_H_VERSION__ 440\n");
+ print_proxy( "#define __REQUIRED_RPCPROXY_H_VERSION__ 440\n");
print_proxy( "#endif /* __REDQ_RPCPROXY_H_VERSION__ */\n");
print_proxy( "\n");
print_proxy( "#include \"rpcproxy.h\"\n");
@@ -124,7 +158,9 @@
while (arg) {
if (is_attr(arg->attrs, ATTR_OUT) && !is_attr(arg->attrs, ATTR_IN)) {
print_proxy( "if(%s)\n", arg->name );
- print_proxy( " MIDL_memset( %s, 0, sizeof( ", arg->name );
+ indent++;
+ print_proxy( "MIDL_memset( %s, 0, sizeof( ", arg->name );
+ indent--;
write_type(proxy, arg->type, arg, arg->tname);
fprintf( proxy, " ));\n" );
}
@@ -132,7 +168,7 @@
}
}
-static void gen_marshall_size( var_t *arg )
+static void proxy_gen_marshall_size( var_t *arg )
{
print_proxy( "_StubMsg.BufferLength = 0U;\n" );
@@ -143,11 +179,7 @@
while (arg) {
if (is_attr(arg->attrs, ATTR_IN)) {
int index = 0;
- type_t *type = arg->type;
-
- /* find the base type */
- while( type->ref )
- type = type->ref;
+ type_t *type = get_base_type(arg->type);
switch( type->type )
{
@@ -173,6 +205,11 @@
fprintf(proxy, "&__MIDL_TypeFormatString.Format[%d] );\n", index );
break;
+ case RPC_FC_IP:
+ print_proxy( "NdrPointerBufferSize( &_StubMsg, (unsigned char*)%s, ", arg->name );
+ fprintf(proxy, "&__MIDL_TypeFormatString.Format[%d]);\n", index );
+ break;
+
default:
printf("FIXME: arg %s has unknown type %d\n", arg->name, type->type );
}
@@ -190,11 +227,7 @@
while (arg) {
if (is_attr(arg->attrs, ATTR_IN)) {
int index = 0;
- type_t *type = arg->type;
-
- /* find the base type */
- while( type->ref )
- type = type->ref;
+ type_t *type = get_base_type(arg->type);
switch( type->type )
{
@@ -217,6 +250,11 @@
fprintf(proxy, "&__MIDL_TypeFormatString.Format[%d]);\n", index );
break;
+ case RPC_FC_IP:
+ print_proxy( "NdrPointerMarshall( &_StubMsg, (unsigned char*)%s, ", arg->name );
+ fprintf(proxy, "&__MIDL_TypeFormatString.Format[%d]);\n", index );
+ break;
+
default:
printf("FIXME: arg %s has unknown type %d\n", arg->name, type->type );
}
@@ -228,7 +266,7 @@
static void gen_marshall( var_t *arg )
{
/* generated code to determine the size of the buffer required */
- gen_marshall_size( arg );
+ proxy_gen_marshall_size( arg );
/* generated code to allocate the buffer */
print_proxy( "NdrProxyGetBuffer(This, &_StubMsg);\n" );
@@ -246,9 +284,8 @@
arg = NEXT_LINK(arg);
}
while (arg) {
- if (is_attr(arg->attrs, ATTR_OUT)) {
+ if (is_attr(arg->attrs, ATTR_IN)) {
int index = 0;
- /* FIXME: add the format string, and set the index below */
print_proxy( "NdrPointerUnmarshall(&_StubMsg, (unsigned char**)&%s, ", arg->name );
fprintf(proxy, "&__MIDL_TypeFormatString.Format[%d], 0);\n", index );
}
@@ -283,11 +320,13 @@
/* FIXME: trace */
clear_output_vars( cur->args );
- print_proxy( "RpcTryExcept {\n" );
+ print_proxy( "RpcTryExcept\n" );
+ print_proxy( "{\n" );
indent++;
print_proxy( "NdrProxyInitialize(This, &_Msg, &_StubMsg, &Object_StubDesc, %d);\n", idx);
- print_proxy( "RpcTryFinally {\n" );
+ print_proxy( "RpcTryFinally\n" );
+ print_proxy( "{\n" );
indent++;
gen_marshall( cur->args );
@@ -311,7 +350,8 @@
indent--;
print_proxy( "}\n");
- print_proxy( "RpcFinally {\n" );
+ print_proxy( "RpcFinally\n" );
+ print_proxy( "{\n" );
indent++;
print_proxy( "NdrProxyFreeBuffer(This, &_StubMsg);\n" );
indent--;
@@ -350,6 +390,151 @@
fprintf(proxy, "\n");
}
+static void stub_unmarshall( var_t *arg )
+{
+ if (arg) {
+ while (NEXT_LINK(arg))
+ arg = NEXT_LINK(arg);
+ }
+ while (arg) {
+ if (is_attr(arg->attrs, ATTR_IN)) {
+ int index = 0;
+ type_t *type = get_base_type(arg->type);
+
+ switch( type->type )
+ {
+ case RPC_FC_BYTE:
+ case RPC_FC_CHAR:
+ case RPC_FC_SHORT:
+ case RPC_FC_USHORT:
+ case RPC_FC_ENUM16:
+ case RPC_FC_LONG:
+ case RPC_FC_ULONG:
+ case RPC_FC_ENUM32:
+ print_proxy( "%s = *((", arg->name);
+ write_type(proxy, arg->type, arg, arg->tname);
+ fprintf(proxy,"*)_StubMsg.Buffer)++;\n");
+ break;
+
+ case RPC_FC_STRUCT:
+ /* FIXME: add the format string, and set the index below */
+ print_proxy( "NdrSimpleStructUnmarshall(&_StubMsg, (unsigned char**)&%s, ", arg->name );
+ fprintf(proxy, "&__MIDL_TypeFormatString.Format[%d],0);\n", index );
+ break;
+
+ default:
+ printf("FIXME: arg %s has unknown type %d\n", arg->name, type->type );
+ }
+ }
+ arg = PREV_LINK(arg);
+ }
+}
+
+static void stub_gen_marshall_size( var_t *arg )
+{
+ print_proxy( "_StubMsg.BufferLength = 0U;\n" );
+
+ if (arg) {
+ while (NEXT_LINK(arg))
+ arg = NEXT_LINK(arg);
+ }
+ while (arg) {
+ if (is_attr(arg->attrs, ATTR_OUT)) {
+ int index = 0;
+ type_t *type = get_base_type(arg->type);
+
+ switch( type->type )
+ {
+ case RPC_FC_BYTE:
+ case RPC_FC_CHAR:
+ print_proxy( "_StubMsg.BufferLength += %d; /* %s */\n", 1, arg->name );
+ break;
+
+ case RPC_FC_SHORT:
+ case RPC_FC_USHORT:
+ case RPC_FC_ENUM16:
+ print_proxy( "_StubMsg.BufferLength += %d; /* %s */\n", 2, arg->name );
+ break;
+
+ case RPC_FC_LONG:
+ case RPC_FC_ULONG:
+ case RPC_FC_ENUM32:
+ print_proxy( "_StubMsg.BufferLength += %d; /* %s */\n", 4, arg->name );
+ break;
+
+ case RPC_FC_STRUCT:
+ print_proxy( "NdrSimpleStructBufferSize(&_StubMsg, (unsigned char*)%s, ", arg->name );
+ fprintf(proxy, "&__MIDL_TypeFormatString.Format[%d] );\n", index );
+ break;
+
+ case RPC_FC_IP:
+ print_proxy( "NdrPointerBufferSize( &_StubMsg, (unsigned char*)%s, ", arg->name );
+ fprintf(proxy, "&__MIDL_TypeFormatString.Format[%d]);\n", index );
+ break;
+
+ default:
+ printf("FIXME: arg %s has unknown type %d\n", arg->name, type->type );
+ }
+ }
+ arg = PREV_LINK(arg);
+ }
+}
+
+static void stub_gen_marshall_copydata( var_t *arg )
+{
+ if (arg) {
+ while (NEXT_LINK(arg))
+ arg = NEXT_LINK(arg);
+ }
+ while (arg) {
+ if (is_attr(arg->attrs, ATTR_OUT)) {
+ int index = 0;
+ type_t *type = get_base_type(arg->type);
+
+ switch( type->type )
+ {
+ case RPC_FC_BYTE:
+ case RPC_FC_CHAR:
+ case RPC_FC_SHORT:
+ case RPC_FC_USHORT:
+ case RPC_FC_ENUM16:
+ case RPC_FC_LONG:
+ case RPC_FC_ULONG:
+ case RPC_FC_ENUM32:
+ print_proxy( "*((");
+ write_type(proxy, arg->type, arg, arg->tname);
+ fprintf(proxy,"*)_StubMsg.Buffer)++ = %s;\n", arg->name );
+ break;
+
+ case RPC_FC_STRUCT:
+ /* FIXME: add the format string, and set the index below */
+ print_proxy( "NdrSimpleStructMarshall(&_StubMsg, (unsigned char*)%s, ", arg->name );
+ fprintf(proxy, "&__MIDL_TypeFormatString.Format[%d]);\n", index );
+ break;
+
+ case RPC_FC_IP:
+ print_proxy( "NdrPointerMarshall( &_StubMsg, (unsigned char*)%s, ", arg->name );
+ fprintf(proxy, "&__MIDL_TypeFormatString.Format[%d]);\n", index );
+ break;
+
+ default:
+ printf("FIXME: arg %s has unknown type %d\n", arg->name, type->type );
+ }
+ }
+ arg = PREV_LINK(arg);
+ }
+}
+
+static void stub_genmarshall( var_t *args )
+{
+ /* FIXME: size buffer */
+ stub_gen_marshall_size( args );
+
+ print_proxy("NdrStubGetBuffer(This, pRpcChannelBuffer, &_StubMsg);\n");
+
+ stub_gen_marshall_copydata( args );
+}
+
static void gen_stub(type_t *iface, func_t *cur, char *cas)
{
var_t *def = cur->def;
@@ -392,10 +577,12 @@
print_proxy("NdrStubInitialize(pRpcMessage, &_StubMsg, &Object_StubDesc, pRpcChannelBuffer);\n");
fprintf(proxy, "\n");
- /* clear output vars */
+ print_proxy("RpcTryFinally\n");
+ print_proxy("{\n");
+ indent++;
stub_clear_output_vars( cur->args );
- /* FIXME: unmarshall */
+ stub_unmarshall( cur->args );
print_proxy("*pdwStubPhase = STUB_CALL_SERVER;\n");
print_proxy("");
@@ -416,9 +603,27 @@
fprintf(proxy, ");\n");
print_proxy("*pdwStubPhase = STUB_MARSHAL;\n");
- /* FIXME: size buffer */
+ stub_genmarshall( cur->args );
- print_proxy("NdrStubGetBuffer(This, pRpcChannelBuffer, &_StubMsg);\n");
+ if (has_ret) {
+ /*
+ * FIXME: We only need to round the buffer up if it could be unaligned...
+ * We should calculate how much buffer we used and output the following
+ * line only if necessary.
+ */
+ print_proxy( "_StubMsg.Buffer = (unsigned char *)(((long)_StubMsg.Buffer + 3) & ~ 0x3);\n");
+
+ print_proxy( "*((" );
+ write_type(proxy, def->type, def, def->tname);
+ fprintf(proxy, "*)_StubMsg.Buffer)++ = _Ret;\n");
+ }
+
+ indent--;
+ print_proxy("}\n");
+ print_proxy("RpcFinally\n");
+ print_proxy("{\n");
+ print_proxy("}\n");
+ print_proxy("RpcEndFinally\n");
/* FIXME: marshall */
indent--;
@@ -511,7 +716,8 @@
write_stubdesc();
/* proxy vtable */
- fprintf(proxy, "const CINTERFACE_PROXY_VTABLE(%d) %sProxyVtbl = {\n", midx, iface->name);
+ fprintf(proxy, "const CINTERFACE_PROXY_VTABLE(%d) %sProxyVtbl =\n", midx, iface->name);
+ fprintf(proxy, "{\n");
fprintf(proxy, " {&IID_%s},\n", iface->name);
fprintf(proxy, " {");
write_proxy_methods(iface);
@@ -520,7 +726,8 @@
fprintf(proxy, "\n");
/* stub vtable */
- fprintf(proxy, "static const PRPC_STUB_FUNCTION %s_table[] = {\n", iface->name);
+ fprintf(proxy, "static const PRPC_STUB_FUNCTION %s_table[] =\n", iface->name);
+ fprintf(proxy, "{\n");
stubs = write_stub_methods(iface);
fprintf(proxy, "\n");
fprintf(proxy, "};\n");
@@ -533,6 +740,8 @@
fprintf(proxy, " {CStdStubBuffer_METHODS}\n");
fprintf(proxy, "};\n");
fprintf(proxy, "\n");
+ write_formatstring( 1 );
+ write_formatstring( 0 );
}
void write_proxies(ifref_t *ifaces)
@@ -554,7 +763,8 @@
if (!proxy) return;
- fprintf(proxy, "const CInterfaceProxyVtbl* _%s_ProxyVtblList[] = {\n", file_id);
+ fprintf(proxy, "const CInterfaceProxyVtbl* _%s_ProxyVtblList[] =\n", file_id);
+ fprintf(proxy, "{\n");
cur = lcur;
while (cur) {
if(cur->iface->ref)
@@ -565,7 +775,8 @@
fprintf(proxy, "};\n");
fprintf(proxy, "\n");
- fprintf(proxy, "const CInterfaceStubVtbl* _%s_StubVtblList[] = {\n", file_id);
+ fprintf(proxy, "const CInterfaceStubVtbl* _%s_StubVtblList[] =\n", file_id);
+ fprintf(proxy, "{\n");
cur = lcur;
while (cur) {
if(cur->iface->ref)
@@ -576,7 +787,8 @@
fprintf(proxy, "};\n");
fprintf(proxy, "\n");
- fprintf(proxy, "const PCInterfaceName _%s_InterfaceNamesList[] = {\n", file_id);
+ fprintf(proxy, "const PCInterfaceName _%s_InterfaceNamesList[] =\n", file_id);
+ fprintf(proxy, "{\n");
cur = lcur;
while (cur) {
if(cur->iface->ref)
@@ -608,14 +820,19 @@
fprintf(proxy, "}\n");
fprintf(proxy, "\n");
- fprintf(proxy, "const ExtendedProxyFileInfo %s_ProxyFileInfo = {\n", file_id);
+ fprintf(proxy, "const ExtendedProxyFileInfo %s_ProxyFileInfo =\n", file_id);
+ fprintf(proxy, "{\n");
fprintf(proxy, " (PCInterfaceProxyVtblList*)&_%s_ProxyVtblList,\n", file_id);
fprintf(proxy, " (PCInterfaceStubVtblList*)&_%s_StubVtblList,\n", file_id);
fprintf(proxy, " (const PCInterfaceName*)&_%s_InterfaceNamesList,\n", file_id);
fprintf(proxy, " 0,\n");
fprintf(proxy, " &_%s_IID_Lookup,\n", file_id);
fprintf(proxy, " %d,\n", c);
- fprintf(proxy, " 1\n");
+ fprintf(proxy, " 1,\n");
+ fprintf(proxy, " 0,\n");
+ fprintf(proxy, " 0,\n");
+ fprintf(proxy, " 0,\n");
+ fprintf(proxy, " 0\n");
fprintf(proxy, "};\n");
fclose(proxy);
More information about the wine-patches
mailing list