Skip to content

Commit 22355ac

Browse files
authored
Merge pull request #156 from jonas/bindings
Add initial bindings subproject
2 parents fc815fe + 380d4f7 commit 22355ac

File tree

22 files changed

+716
-35
lines changed

22 files changed

+716
-35
lines changed

.scalafmt.conf

+2-1
Original file line numberDiff line numberDiff line change
@@ -2,9 +2,10 @@ style = defaultWithAlign
22
docstrings = JavaDoc
33
assumeStandardLibraryStripMargin = true
44
project.excludeFilters = [
5-
"tests/samples/[^/]*[.]scala"
5+
"bindings/[^/]+/src/main/.*[.]scala"
66
"docs/src/test/scala/org/example/.*[.]scala"
77
"sbt-scala-native-bindgen/.*/expected/.*[.]scala"
8+
"tests/samples/[^/]*[.]scala"
89
]
910
project.git = true
1011
runner.dialect = Scala211

Dockerfile

+16
Original file line numberDiff line numberDiff line change
@@ -10,12 +10,18 @@ RUN set -x \
1010
&& apt-key adv --keyserver hkp://keyserver.ubuntu.com:80 --recv 2EE0EA64E40A89B84B2DF73499E82A75642AC823 \
1111
&& apt update \
1212
&& apt install -y --no-install-recommends \
13+
locales locales-all \
1314
g++ openjdk-8-jdk-headless sbt cmake make curl git \
1415
zlib1g-dev \
1516
libgc-dev libunwind8-dev libre2-dev \
1617
nlohmann-json-dev \
1718
&& rm -rf /var/lib/apt/lists/*
1819

20+
ARG LOCALE=en_US.UTF-8
21+
ENV LANG=$LOCALE
22+
ENV LANGUAGE=$LOCALE
23+
ENV LC_ALL=$LOCALE
24+
1925
ARG LLVM_VERSION=6.0
2026
ENV LLVM_VERSION=$LLVM_VERSION
2127
RUN set -x \
@@ -26,4 +32,14 @@ RUN set -x \
2632
&& rm -rf /var/lib/apt/lists/*
2733

2834
ENV PATH=$PATH:/usr/lib/llvm-$LLVM_VERSION/bin
35+
36+
##bindings-dev-package
37+
# Install binding dependencies
38+
RUN set -x \
39+
&& apt update \
40+
&& apt install -y --no-install-recommends \
41+
libutf8proc-dev \
42+
&& rm -rf /var/lib/apt/lists/*
43+
##bindings-dev-package
44+
2945
WORKDIR /src
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,16 @@
1+
package org.scalanative.bindgen.bindings.iconv
2+
3+
import scala.scalanative._
4+
import scala.scalanative.native._
5+
6+
@native.extern
7+
object iconv {
8+
type iconv_t = native.Ptr[Byte]
9+
def iconv_open(__tocode: native.CString, __fromcode: native.CString): native.Ptr[Byte] = native.extern
10+
def iconv(__cd: native.Ptr[Byte], __inbuf: native.Ptr[native.CString], __inbytesleft: native.Ptr[native.CSize], __outbuf: native.Ptr[native.CString], __outbytesleft: native.Ptr[native.CSize]): native.CSize = native.extern
11+
def iconv_close(__cd: native.Ptr[Byte]): native.CInt = native.extern
12+
13+
object defines {
14+
val _ICONV_H: native.CInt = 1
15+
}
16+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,72 @@
1+
package org.scalanative.bindgen.bindings.iconv.tests
2+
3+
import org.scalatest.FunSpec
4+
5+
class IconvSpec extends FunSpec {
6+
describe("iconv") {
7+
it("should convert back and forth between UTF-8 and ISO-8859-1") {
8+
//#usage-example
9+
import org.scalanative.bindgen.bindings.iconv.iconv._
10+
import scala.scalanative.native._
11+
import java.nio.charset.Charset
12+
13+
val UTF8 = Charset.forName("UTF-8")
14+
val encode = iconv_open(c"UTF-8", c"ISO-8859-1")
15+
val decode = iconv_open(c"ISO-8859-1", c"UTF-8")
16+
17+
Zone { implicit zone =>
18+
val originalBuf = toCString("øre", UTF8) // Ear in Danish
19+
val originalBufPtr = alloc[CString]
20+
!originalBufPtr = originalBuf
21+
val originalBytesLeft = alloc[CSize]
22+
!originalBytesLeft = string.strlen(originalBuf)
23+
//#usage-example
24+
assert(!originalBytesLeft == 4)
25+
//#usage-example
26+
27+
val translatedBuf = alloc[Byte](32)
28+
val translatedBufPtr = alloc[CString]
29+
!translatedBufPtr = translatedBuf
30+
val translatedBytesLeft = alloc[CSize]
31+
!translatedBytesLeft = 32
32+
33+
val translatedCode = iconv(
34+
encode,
35+
originalBufPtr,
36+
originalBytesLeft,
37+
translatedBufPtr,
38+
translatedBytesLeft
39+
)
40+
//#usage-example
41+
42+
assert(translatedCode == 0)
43+
44+
!translatedBufPtr = translatedBuf
45+
!translatedBytesLeft = string.strlen(translatedBuf)
46+
47+
val roundtripBuf = alloc[Byte](32)
48+
val roundtripBufPtr = alloc[CString]
49+
!roundtripBufPtr = roundtripBuf
50+
val roundtripBytesLeft = alloc[CSize]
51+
!roundtripBytesLeft = 32
52+
53+
val roundtripCode = iconv(
54+
decode,
55+
translatedBufPtr,
56+
translatedBytesLeft,
57+
roundtripBufPtr,
58+
roundtripBytesLeft
59+
)
60+
61+
assert(string.strcmp(originalBuf, roundtripBuf) == 0)
62+
//#usage-example
63+
}
64+
//#usage-example
65+
66+
//#usage-example
67+
iconv_close(encode)
68+
//#usage-example
69+
iconv_close(decode)
70+
}
71+
}
72+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,14 @@
1+
package org.scalanative.bindgen.bindings.posix
2+
3+
import scala.scalanative._
4+
import scala.scalanative.native._
5+
6+
@native.extern
7+
object fnmatch {
8+
def fnmatch(__pattern: native.CString, __name: native.CString, __flags: native.CInt): native.CInt = native.extern
9+
10+
object defines {
11+
val _FNMATCH_H: native.CInt = 1
12+
val FNM_NOMATCH: native.CInt = 1
13+
}
14+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,59 @@
1+
package org.scalanative.bindgen.bindings.posix
2+
3+
import scala.scalanative._
4+
import scala.scalanative.native._
5+
6+
@native.extern
7+
object regex {
8+
type enum_reg_errcode_t = native.CUnsignedInt
9+
object enum_reg_errcode_t {
10+
final val REG_NOERROR: enum_reg_errcode_t = 0.toUInt
11+
final val REG_NOMATCH: enum_reg_errcode_t = 1.toUInt
12+
final val REG_BADPAT: enum_reg_errcode_t = 2.toUInt
13+
final val REG_ECOLLATE: enum_reg_errcode_t = 3.toUInt
14+
final val REG_ECTYPE: enum_reg_errcode_t = 4.toUInt
15+
final val REG_EESCAPE: enum_reg_errcode_t = 5.toUInt
16+
final val REG_ESUBREG: enum_reg_errcode_t = 6.toUInt
17+
final val REG_EBRACK: enum_reg_errcode_t = 7.toUInt
18+
final val REG_EPAREN: enum_reg_errcode_t = 8.toUInt
19+
final val REG_EBRACE: enum_reg_errcode_t = 9.toUInt
20+
final val REG_BADBR: enum_reg_errcode_t = 10.toUInt
21+
final val REG_ERANGE: enum_reg_errcode_t = 11.toUInt
22+
final val REG_ESPACE: enum_reg_errcode_t = 12.toUInt
23+
final val REG_BADRPT: enum_reg_errcode_t = 13.toUInt
24+
final val REG_EEND: enum_reg_errcode_t = 14.toUInt
25+
final val REG_ESIZE: enum_reg_errcode_t = 15.toUInt
26+
final val REG_ERPAREN: enum_reg_errcode_t = 16.toUInt
27+
}
28+
29+
type s_reg_t = native.CLong
30+
type active_reg_t = native.CUnsignedLong
31+
type reg_syntax_t = native.CUnsignedLong
32+
type reg_errcode_t = enum_reg_errcode_t
33+
type struct_re_pattern_buffer = native.CArray[Byte, native.Nat.Digit[native.Nat._6, native.Nat._4]]
34+
type regex_t = struct_re_pattern_buffer
35+
type regoff_t = native.CInt
36+
type struct_regmatch_t = native.CStruct2[regoff_t, regoff_t]
37+
type regmatch_t = struct_regmatch_t
38+
val re_syntax_options: reg_syntax_t = native.extern
39+
def regcomp(__preg: native.Ptr[regex_t], __pattern: native.CString, __cflags: native.CInt): native.CInt = native.extern
40+
def regexec(__preg: native.Ptr[regex_t], __string: native.CString, __nmatch: native.CSize, __pmatch: native.Ptr[regmatch_t], __eflags: native.CInt): native.CInt = native.extern
41+
def regerror(__errcode: native.CInt, __preg: native.Ptr[regex_t], __errbuf: native.CString, __errbuf_size: native.CSize): native.CSize = native.extern
42+
def regfree(__preg: native.Ptr[regex_t]): Unit = native.extern
43+
44+
object defines {
45+
val _REGEX_H: native.CInt = 1
46+
val REG_EXTENDED: native.CInt = 1
47+
val REG_NOTBOL: native.CInt = 1
48+
}
49+
50+
object implicits {
51+
implicit class struct_regmatch_t_ops(val p: native.Ptr[struct_regmatch_t]) extends AnyVal {
52+
def rm_so: regoff_t = !p._1
53+
def rm_so_=(value: regoff_t): Unit = !p._1 = value
54+
def rm_eo: regoff_t = !p._2
55+
def rm_eo_=(value: regoff_t): Unit = !p._2 = value
56+
}
57+
def struct_regmatch_t()(implicit z: native.Zone): native.Ptr[struct_regmatch_t] = native.alloc[struct_regmatch_t]
58+
}
59+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,19 @@
1+
package org.scalanative.bindgen.bindings.tests
2+
3+
import org.scalatest.FunSpec
4+
5+
class FnmatchSpec extends FunSpec {
6+
describe("fnmatch") {
7+
it("should match patterns") {
8+
//#usage-example
9+
import scala.scalanative.native._
10+
import org.scalanative.bindgen.bindings.posix.fnmatch._
11+
12+
assert(fnmatch(c"*.md", c"README.md", 0) == 0)
13+
assert(fnmatch(c"*.[ch]", c"main.h", 0) == 0)
14+
assert(fnmatch(c"*.[ch]", c"main.c", 0) == 0)
15+
assert(fnmatch(c"*.md", c"README_md", 0) == defines.FNM_NOMATCH)
16+
//#usage-example
17+
}
18+
}
19+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,27 @@
1+
package org.scalanative.bindgen.bindings.tests
2+
3+
import org.scalatest.FunSpec
4+
5+
class RegexSpec extends FunSpec {
6+
describe("regex") {
7+
it("should match regular expressions") {
8+
//#usage-example
9+
import scala.scalanative.native._
10+
import org.scalanative.bindgen.bindings.posix.regex._
11+
12+
val reg = stackalloc[regex_t]
13+
14+
val compResult =
15+
regcomp(reg, c"Scala \\(\\(J\\(VM\\|S\\)\\)\\|Native\\)", 0)
16+
assert(compResult == 0)
17+
18+
assert(regexec(reg, c"Scala JVM", 0, null, 0) == 0)
19+
assert(regexec(reg, c"Scala JS", 0, null, 0) == 0)
20+
assert(regexec(reg, c"Scala Native", 0, null, 0) == 0)
21+
assert(regexec(reg, c"Scala .NET", 0, null, 0) != 0)
22+
23+
regfree(reg)
24+
//#usage-example
25+
}
26+
}
27+
}

0 commit comments

Comments
 (0)