Small fixes
[panamaz] / src / generate-native
index d8d2497..b17434c 100755 (executable)
@@ -184,6 +184,12 @@ sub findRoots {
                                foreach $func (@list) {
                                        $seen{"func:$func->{name}"} ++;
                                }
+                       } elsif ($inc->{mode} eq 'call') {
+                               my @list = grep { $_->{type} eq $inc->{mode} && $_->{name} =~ m/$inc->{regex}/ } values %data;
+
+                               foreach $func (@list) {
+                                       $seen{"call:$func->{name}"} ++;
+                               }
                        }
                }
        }
@@ -313,7 +319,7 @@ sub analyseAPI {
                        } elsif ($o =~ m/^access=([rwi]+)$/) {
                                $obj->{access} = $1;
                        } elsif ($o =~ m/^success=(.*)$/) {
-                               # for functions
+                               # for functions?
                                $obj->{success} = $1;
                        } elsif ($o =~ m@^(rename|field:rename|func:rename)=(.*)@) {
                                my $target = $1;
@@ -336,10 +342,10 @@ sub analyseAPI {
                my $defmode = $obj->{type} eq 'library' ? 'func' : 'field';
 
                foreach $inc (@{$obj->{items}}) {
-                       if ($inc->{match} =~ m@^(field|func|define|struct|enum):/(.*)/$@) {
+                       if ($inc->{match} =~ m@^(field|func|define|struct|enum|call):/(.*)/$@) {
                                $inc->{regex} = qr/$2/;
                                $inc->{mode} = $1; # ?? "$1-include";
-                       } elsif ($inc->{match} =~ m@^(field|func|define|struct|enum):(.*)$@) {
+                       } elsif ($inc->{match} =~ m@^(field|func|define|struct|enum|call):(.*)$@) {
                                $inc->{regex} = qr/^$2$/;
                                $inc->{mode} = $1;
                        } elsif ($inc->{match} =~ m@^/(.*)/$@) {
@@ -547,7 +553,7 @@ sub formatTypeLayout {
 }
 
 sub formatFunctionDescriptor {
-       my $c = shift @_;
+       my $c = shift;
        my @arguments = @{$c->{arguments}};
        my $result = $c->{result};
        my $desc;
@@ -862,6 +868,7 @@ sub formatFunction {
                my $r = $c->{result_code};
                $desc .= "$r->{typeInfo}->{type} $r->{name}\$value;\n";
        }
+       $desc .= "$result->{typeInfo}->{carrier} res\$value;\n" if ($rtype ne "void");
 
        $desc .= " try ";
        $desc .= "(Frame frame = Memory.createFrame()) " if ($c->{resolveFrame});
@@ -872,7 +879,7 @@ sub formatFunction {
                $desc .= "  $r->{typeInfo}->{declare};\n";
        }
 
-       $desc .= "  $result->{typeInfo}->{carrier} res\$value = ($result->{typeInfo}->{carrier})" if ($rtype ne "void");
+       $desc .= "  res\$value = ($result->{typeInfo}->{carrier})" if ($rtype ne "void");
        $desc .= "  " if ($rtype eq "void");
 
        $index = 0;
@@ -896,6 +903,8 @@ sub formatFunction {
        }
        $desc .= ");\n";
 
+       my $error_value;
+
        if ($rtype ne "void") {
                my $create = $result->{typeInfo}->{create};
 
@@ -908,16 +917,27 @@ sub formatFunction {
                        $create =~ s/\$\{scope\}/scope()/;
                }
 
+               my $success;
+
                if ($c->{result_code}) {
                        my $r = $c->{result_code};
-                       my $success = $c->{success} ? $c->{success} : '0';
 
-                       $desc .= "  $r->{name}\$value = $r->{name}.get(0);\n";
+                       $error_value = "$r->{name}\$value";
+                       $desc .= "  $error_value = $r->{name}.get(0);\n";
+                       $success = $c->{success} ? $c->{success} : '0';
+               } elsif ($c->{success}) {
+                       $success = $c->{success};
+                       $error_value = "res\$value";
+               } elsif ($inc->{success}) {
+                       $success = $inc->{success};
+                       $error_value = "res\$value";
+               }
+               if ($success) {
                        $desc .= "  if (";
                        $count = 0;
                        foreach $s (split /,/,$success) {
                                $desc .= " || " if ($count++ > 0);
-                               $desc .= "($r->{name}\$value == $s)";
+                               $desc .= "($error_value == $s)";
                        }
                        $desc .= ")\n";
                }
@@ -928,9 +948,8 @@ sub formatFunction {
        $desc .= " } catch (Throwable t) { throw new RuntimeException(t); }\n";
 
        # assume it's an int
-       if ($c->{result_code}) {
-               my $r = $c->{result_code};
-               $desc .= " throw new RuntimeException(String.format(\"error=%d\", $r->{name}\$value));\n";
+       if ($error_value) {
+               $desc .= " throw new RuntimeException(String.format(\"error=%d\", $error_value));\n";
        }
 
        $desc .="}";
@@ -1278,7 +1297,7 @@ sub exportStruct {
 
        # TODO: parameterise and use typeInfo data.
        if (!$isHandle) {
-               print $f " MemorySegment segment;\n";
+               print $f " public final MemorySegment segment;\n";
                # constructors
                print $f " private $s->{name}(MemorySegment segment) { this.segment = segment; }\n";
                print $f " public static $s->{name} create(MemorySegment segment) { return new $s->{name}(segment); }\n";
@@ -1514,9 +1533,27 @@ foreach $obj ( @{$api->{struct}} ) {
        }
 }
 
+# find flag
+sub flag {
+       my $obj = shift;
+       my $flag = shift;
+
+       return grep { $_ eq $flag } @{$obj->{options}};
+}
+
+# find option(s)
+sub option {
+       my $obj = shift;
+       my $name = shift;
+       my $rx = qr/^$name=/;
+
+       return grep { $_ =~ m/$rx/ } @{$obj->{options}};
+}
+
 # Dump library type
 foreach $lib ( @{$api->{library}} ) {
        my $path = nameToPath($output, "$package.$lib->{name}");
+       my $dynamic = flag($lib, 'dynamic');
 
        open (my $f, ">", $path) || die ("Cannot open '$path' for writing");
 
@@ -1525,10 +1562,8 @@ foreach $lib ( @{$api->{library}} ) {
        print $f "import java.lang.invoke.*;\n";
 
        print $f "public class $lib->{name} {\n";
-
        print $f " static ResourceScope scope() { return ResourceScope.globalScope(); }\n";
 
-       # scan for matches
        foreach $inc (@{$lib->{items}}) {
                if ($inc->{mode} eq 'func') {
                        my @list = grep { $_->{type} eq $inc->{mode} && $_->{name} =~ m/$inc->{regex}/ } values %data;