1
0
mirror of https://github.com/samba-team/samba.git synced 2025-12-07 20:23:50 +03:00
Files
samba-mirror/source/pidl/lib/Parse/Pidl/Samba4/SWIG.pm

178 lines
3.7 KiB
Perl

###################################################
# Samba4 parser generator for swig wrappers
# Copyright tpot@samba.org 2004,2005
# Copyright jelmer@samba.org 2006
# released under the GNU GPL
package Parse::Pidl::Samba4::SWIG;
use vars qw($VERSION);
use Parse::Pidl::Samba4 qw(DeclLong);
use Parse::Pidl::Typelist qw(mapTypeName);
use Parse::Pidl::Util qw(has_property);
$VERSION = '0.01';
use strict;
my $ret = "";
my $tabs = "";
sub pidl($)
{
my $p = shift;
$ret .= $tabs. $p . "\n";
}
sub indent() { $tabs.=" "; }
sub deindent() { $tabs = substr($tabs,0,-2); }
sub IgnoreInterface($$)
{
my ($basename,$if) = @_;
foreach (@{$if->{TYPES}}) {
next unless (has_property($_, "public"));
pidl "\%types($_->{NAME});";
}
}
sub GenerateResultTypemap($)
{
my $name = shift;
pidl "%typemap(in,numinputs=0) $name*result ($name tmp) {";
indent;
pidl "\$1 = &tmp;";
deindent;
pidl "}";
pidl "";
pidl "%typemap(argout) $name*result {";
indent;
pidl "\$result = SWIG_NewPointerObj(*\$1, \$1_descriptor, 0);";
deindent;
pidl "}";
}
sub ParseInterface($$)
{
my ($basename,$if) = @_;
pidl "\%inline {";
pidl "typedef struct $if->{NAME} { struct dcerpc_pipe *pipe; } $if->{NAME};";
pidl "}";
pidl "";
pidl "%talloctype($if->{NAME});";
pidl "";
pidl "\%extend $if->{NAME} {";
indent();
pidl "$if->{NAME} () {";
indent;
pidl "return talloc(NULL, struct $if->{NAME});";
deindent;
pidl "}";
pidl "";
pidl "NTSTATUS connect (const char *binding, struct cli_credentials *cred, struct event_context *event)";
pidl "{";
indent;
pidl "return dcerpc_pipe_connect(\$self, &\$self->pipe, binding, &ndr_table_$if->{NAME}, cred, event);";
deindent;
pidl "}";
pidl "";
foreach my $fn (@{$if->{FUNCTIONS}}) {
pidl "/* $fn->{NAME} */";
my $args = "";
foreach (@{$fn->{ELEMENTS}}) {
$args .= DeclLong($_) . ", ";
}
my $name = $fn->{NAME};
$name =~ s/^$if->{NAME}_//g;
$name =~ s/^$basename\_//g;
$args .= "TALLOC_CTX *mem_ctx, " . mapTypeName($fn->{RETURN_TYPE}) . " *result";
pidl "NTSTATUS $name($args)";
pidl "{";
indent;
pidl "struct $fn->{NAME} r;";
pidl "NTSTATUS status;";
pidl "";
pidl "/* Fill r structure */";
foreach (@{$fn->{ELEMENTS}}) {
if (grep(/in/, @{$_->{DIRECTION}})) {
pidl "r.in.$_->{NAME} = $_->{NAME};";
}
}
pidl "";
pidl "status = dcerpc_$fn->{NAME}(\$self->pipe, mem_ctx, &r);";
pidl "if (NT_STATUS_IS_ERR(status)) {";
indent; pidl "return status;"; deindent;
pidl "}";
pidl "";
pidl "/* Set out arguments */";
foreach (@{$fn->{ELEMENTS}}) {
next unless (grep(/out/, @{$_->{DIRECTION}}));
pidl ("/* FIXME: $_->{NAME} [out] argument is not a pointer */") if ($_->{LEVELS}[0]->{TYPE} ne "POINTER");
pidl "*$_->{NAME} = *r.out.$_->{NAME};";
}
if (defined($fn->{RETURN_TYPE})) {
pidl "*result = r.out.result;";
}
pidl "return NT_STATUS_OK;";
deindent;
pidl "}";
pidl "";
}
deindent();
pidl "};";
pidl "";
foreach (@{$if->{TYPES}}) {
pidl "/* $_->{NAME} */";
}
pidl "";
}
sub Parse($$$$)
{
my($ndr,$basename,$header,$gen_header) = @_;
$ret = "";
pidl "/* This file is autogenerated by pidl. DO NOT EDIT */";
pidl "\%module $basename";
pidl "";
pidl "\%{";
pidl "#include \"includes.h\"";
pidl "#include \"$header\"";
pidl "#include \"$gen_header\"";
pidl "%}";
pidl "\%import \"../rpc/dcerpc.i\"";
pidl "\%import \"../../libcli/util/errors.i\"";
pidl "\%import \"../../lib/talloc/talloc.i\"";
pidl "";
foreach (@$ndr) {
IgnoreInterface($basename, $_) if ($_->{TYPE} eq "INTERFACE");
}
pidl "";
pidl "";
foreach (@$ndr) {
ParseInterface($basename, $_) if ($_->{TYPE} eq "INTERFACE");
}
#FIXME: Foreach ref pointer, set NONNULL
#FIXME: Foreach unique/full pointer, set MAYBENULL
#FIXME: Foreach [out] parameter, set OUTPARAM
return $ret;
}
1;