11 if ($m->{scope} =~ m/^explicit/) {
13 } elsif ($m->{scope} eq 'instance') {
16 'ResourceScope.globalScope()';
19 sub fieldScopeAction {
22 if ($m->{field}->{scope} =~ m/^explicit,(.*)$/) {
23 return code::formatTemplate("scope\$.addCloseAction(() -> $1", { %{$m->{match}}, value => 'res$' });
24 } elsif ($m->{field}->{scope} =~ m/^explicit$/) {
25 'scope$.addCloseAction(() -> res$.close());';
33 return code::formatTemplate($t, $m->{match});
40 my @members = code::scanFields($api, $c);
41 my $result = shift @members;
45 arguments => \@members,
46 vars => \%{$api->{vars}},
49 my $info = $self->{vars};
51 $info->{name} = $c->{name};
52 $info->{rename} = $c->{rename};
54 my @list = map { apply('{type} {name}', $_) } grep { $_->{field}->{output} } @members;
55 push @list, 'ResourceScope scope$' if ($c->{scope} =~ m/explicit/);
56 $info->{'java-arguments'} = join ', ', @list;
57 $info->{'native-arguments'} = join ', ', map { apply('{carrier} {name}', $_) } @members;
59 # for native downcalls
60 $info->{'native-result-define'} = ($result->{match}->{type} ne 'void') ? apply('{carrier} result$;', $result) : '';
61 $info->{'native-result-assign'} = ($result->{match}->{type} ne 'void') ? apply('result$ = ({carrier})', $result) : '';
62 $info->{'native-call'} = join ', ', map {
66 "(jdk.incubator.foreign.Addressable)address()";
68 my $name = $_->{match}->{name};
70 if ($m->{output} == 0 && ($m->{deref} =~ m/^u64:/)) {
72 } elsif ($m->{output} == 0 && $m->{implied}) {
73 $name = $m->{implied};
74 } elsif (defined($m->{'array-size-source'})) {
76 $name = "Memory.size($m->{'array-size-source'}->{name})";
78 code::formatTemplate("{tonative}", { %{$_->{match}}, value=>$name })
83 $info->{'java-call'} = join ', ', map { code::formatTemplate('{tojava}', { %{$_->{match}}, value=>'{name}' }) } grep { $_->{field}->{output} } @members;
85 $info->{'java-signature'} = code::formatFunctionSignature($api, [$result, @members]);
86 $info->{'function-descriptor'} = code::formatFunctionDescriptor($api, [$result, @members]);
88 # hidden output arguments
89 # TODO: what about in/out arguments? they just fall out by not specifying them as scoped?
90 my @output = grep { $_->{field}->{output} == 0 && ($_->{field}->{deref} =~ m/^u64:/) && $_->{field}->{instance} == 0} @members;
92 $info->{'native-output-define'} = join "\n\t\t", map { apply('{carrieri} {name};', $_) } @output;
93 $info->{'native-output-init'} = join ";\n\t\t\t", map { apply('{type} {name}$h = {type}.createArray(1, frame$);', $_) } @output;
94 $info->{'native-output-copy'} = join ";\n\t\t\t", map { apply('{name} = {name}$h.get(0);', $_) } @output;
96 # also required for some tonative types?
97 my $x = grep { $_->{match}->{type} eq 'String' } @members;
98 $info->{'create-frame'} = ($#output >= 0 || grep { $_->{match}->{type} eq 'String' } @members) ? '(Frame frame$ = Memory.createFrame()) ' : '';
100 # result code handling
102 $info->{'result-code'} = $c->{success}->{name};
105 if ($c->{success}->{success} eq '!null') {
106 $info->{'result-test'} = "if ($c->{success}->{name} != MemoryAddress.NULL) ";
107 $info->{'result-throw'} = 'throw new NullPointerException();';
109 $info->{'result-test'} = 'if ('.join('||', map { "$c->{success}->{name} == $_" } split(/,/,$c->{success}->{success})).') ';
110 $info->{'result-throw'} = 'throw new RuntimeException("error="+'.$c->{success}->{name}.');';
113 $info->{'result-test'} = '';
114 $info->{'result-throw'} = '';
120 push @onsuccess, code::findCode($api, $c->{onsuccess}) if defined($c->{onsuccess});
122 if (defined($c->{return})) {
123 # nb: this is only used for output parameters
124 my $res = (grep { $_->{field} == $c->{return} } $result, @members)[0];
126 $info->{'java-result'} = $res->{match}->{typei};
127 push @onsuccess, fieldScopeAction($res);
128 #push @onsuccess, code::formatTemplate('return {tojavai};', { %{$res->{match}}, value => $res->{field}->{name}, scope=>fieldScope($res->{field}) });
130 $info->{'java-result-assign'} = code::formatTemplate('{typei} res$ = {tojavai};', { %{$res->{match}}, value => $res->{field}->{name}, scope=>fieldScope($res->{field}) });
131 $info->{'java-result-return'} = 'return res$;';
132 $info->{'trampoline-result-define'} = 'error';
133 $info->{'trampoline-result-return'} = 'error';
134 } elsif ($result->{field}->{output} && $result->{match}->{type} ne 'void') {
135 $info->{'java-result'} = $result->{match}->{type};
136 push @onsuccess, fieldScopeAction($result);
138 $info->{'java-result-assign'} = code::formatTemplate('{type} res$ = {tojava};', { %{$result->{match}}, value => 'result$', scope=>fieldScope($result->{field}) });
139 $info->{'java-result-return'} = 'return res$;';
141 $info->{'trampoline-result-define'} = apply('{type} res$ = ', $result);
142 $info->{'trampoline-result-return'} = code::formatTemplate('return {tonative};', { %{$result->{match}}, value => 'res$' });
144 $info->{'java-result'} = 'void';
145 $info->{'java-result-assign'} = '';
146 $info->{'java-result-return'} = 'return;';
147 $info->{'trampoline-result-define'} = '';
148 $info->{'trampoline-result-return'} = '';
150 $info->{'on-success'} = join("\n\t\t\t\t", @onsuccess);
152 $info->{'static'} = $c->{static} ? 'static ' : '';