Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Generate extern variable declarations #80

Merged
merged 2 commits into from
Jun 29, 2018
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 4 additions & 0 deletions bindgen/ir/IR.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -95,6 +95,10 @@ llvm::raw_ostream &operator<<(llvm::raw_ostream &s, const IR &ir) {
s << *typeDef;
}

for (const auto &variable : ir.variables) {
s << *variable;
}

for (const auto &varDefine : ir.varDefines) {
s << *varDefine;
}
Expand Down
1 change: 0 additions & 1 deletion bindgen/ir/VarDefine.h
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,6 @@

#include "Define.h"
#include "Variable.h"
#include <llvm/Support/raw_ostream.h>

/**
* Stores a pointer to Variable instance from IR
Expand Down
6 changes: 6 additions & 0 deletions bindgen/ir/Variable.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -2,3 +2,9 @@

Variable::Variable(const std::string &name, std::shared_ptr<Type> type)
: TypeAndName(name, type) {}

llvm::raw_ostream &operator<<(llvm::raw_ostream &s, const Variable &variable) {
s << " val " << variable.getName() << ": " << variable.getType()->str()
<< " = native.extern\n";
return s;
}
4 changes: 4 additions & 0 deletions bindgen/ir/Variable.h
Original file line number Diff line number Diff line change
Expand Up @@ -2,10 +2,14 @@
#define SCALA_NATIVE_BINDGEN_VARIABLE_H

#include "TypeAndName.h"
#include <llvm/Support/raw_ostream.h>

class Variable : public TypeAndName {
public:
Variable(const std::string &name, std::shared_ptr<Type> type);

friend llvm::raw_ostream &operator<<(llvm::raw_ostream &s,
const Variable &variable);
};

#endif // SCALA_NATIVE_BINDGEN_VARIABLE_H
9 changes: 9 additions & 0 deletions tests/samples/Extern.c
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
#include "Extern.h"

int forty_two = 42;
const char version[] = "0.1.0";

enum mode mode = USER;

struct version semver_instance = {.major = 1, .minor = 2, .patch = 3};
struct version *semver = &semver_instance;
12 changes: 12 additions & 0 deletions tests/samples/Extern.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
extern int forty_two;
extern const char version[];

enum mode { SYSTEM, USER };
extern enum mode mode;

struct version {
int major;
int minor;
int patch;
};
extern struct version *semver;
36 changes: 36 additions & 0 deletions tests/samples/Extern.scala
Original file line number Diff line number Diff line change
@@ -0,0 +1,36 @@
package org.scalanative.bindgen.samples

import scala.scalanative._
import scala.scalanative.native._

@native.link("bindgentests")
@native.extern
object Extern {
type enum_mode = native.CUnsignedInt
type struct_version = native.CStruct3[native.CInt, native.CInt, native.CInt]
val forty_two: native.CInt = native.extern
val version: native.CString = native.extern
val mode: enum_mode = native.extern
val semver: native.Ptr[struct_version] = native.extern
}

import Extern._

object ExternEnums {
final val enum_mode_SYSTEM: enum_mode = 0.toUInt
final val enum_mode_USER: enum_mode = 1.toUInt
}

object ExternHelpers {

implicit class struct_version_ops(val p: native.Ptr[struct_version]) extends AnyVal {
def major: native.CInt = !p._1
def major_=(value: native.CInt):Unit = !p._1 = value
def minor: native.CInt = !p._2
def minor_=(value: native.CInt):Unit = !p._2 = value
def patch: native.CInt = !p._3
def patch_=(value: native.CInt):Unit = !p._3 = value
}

def struct_version()(implicit z: native.Zone): native.Ptr[struct_version] = native.alloc[struct_version]
}
5 changes: 5 additions & 0 deletions tests/samples/VarDefine.scala
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,11 @@ import scala.scalanative.native._
@native.link("bindgentests")
@native.extern
object VarDefine {
val a: native.CInt = native.extern
val constInt: native.CInt = native.extern
val constIntPointer: native.Ptr[native.CInt] = native.extern
val c: native.CInt = native.extern
val f: native.CFloat = native.extern
@name("a")
val A: native.CInt = native.extern
@name("constInt")
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
package org.scalanative.bindgen.samples

import utest._
import scalanative.native._

object ExternTests extends TestSuite {
val tests = Tests {
'forty_two - {
assert(Extern.forty_two == 42)
}

'mode - {
assert(Extern.mode == ExternEnums.enum_mode_USER)
}

'semver - {
import ExternHelpers._
assert(Extern.semver.major == 1 && Extern.semver.minor == 2 && Extern.semver.patch == 3)
}
}
}