diff --git a/klang/klang/.gitignore b/klang/klang/.gitignore index f6ef9d9c..584c5af5 100644 --- a/klang/klang/.gitignore +++ b/klang/klang/.gitignore @@ -45,3 +45,4 @@ bin/ ## use to integration ## /src/test/c/SDL2/ +/src/test/c/c/ diff --git a/klang/klang/build.gradle.kts b/klang/klang/build.gradle.kts index 06868695..aacb88e6 100644 --- a/klang/klang/build.gradle.kts +++ b/klang/klang/build.gradle.kts @@ -35,16 +35,24 @@ dependencies { testImplementation(libs.kotest) } -task("unzipSDL2") { +val unzipSDL2 = task("unzipSDL2") { val cSourceDir = "$projectDir/src/test/c/" val zipTree = zipTree(file("${cSourceDir}SDL2-headers.zip")) from(zipTree) into(cSourceDir) } +val unzipCHeaders = task("unzipCHeaders") { + val cSourceDir = "$projectDir/src/test/c/" + val zipTree = zipTree(file("${cSourceDir}c-headers.zip")) + from(zipTree) + into(cSourceDir) +} + tasks.withType().configureEach { options.compilerArgs.add("--enable-preview") - dependsOn("unzipSDL2") + //dependsOn(unzipSDL2) + dependsOn(unzipCHeaders) } tasks.withType().configureEach { diff --git a/klang/klang/src/main/kotlin/klang/parser/libclang/LibClangParser.kt b/klang/klang/src/main/kotlin/klang/parser/libclang/LibClangParser.kt index d5913e2e..37dc85f4 100644 --- a/klang/klang/src/main/kotlin/klang/parser/libclang/LibClangParser.kt +++ b/klang/klang/src/main/kotlin/klang/parser/libclang/LibClangParser.kt @@ -2,19 +2,41 @@ package klang.parser.libclang import klang.DeclarationRepository import java.io.File +import java.nio.file.Path +import kotlin.io.path.exists enum class ParserTechnology { JNA, Panama } -fun parseFile(fileAsString: String, parserTechnology: ParserTechnology = ParserTechnology.Panama): DeclarationRepository { - val file = File(fileAsString) - assert(file.exists()) - return parseFile(file, parserTechnology) +fun parseFile( + fileAsString: String, + filePathAsString: String? = null, + headerPathsAsString: Array = arrayOf(), + parserTechnology: ParserTechnology = ParserTechnology.Panama +): DeclarationRepository { + val file = when (filePathAsString != null) { + true -> filePathAsString.let { "$it/$fileAsString" } + .let(::File) + false -> File(fileAsString) + }.also { assert(it.exists()) } + val path = filePathAsString?.let { Path.of(it) } + ?.also { assert(it.exists()) } + val headerPaths = headerPathsAsString.map { Path.of(it).also { assert(it.exists()) } }.toTypedArray() + return parseFile(file, path, headerPaths, parserTechnology) } -internal fun parseFile(file: File, parserTechnology: ParserTechnology = ParserTechnology.Panama) = when (parserTechnology) { - ParserTechnology.JNA -> parseFileWithJna(file.absolutePath) - ParserTechnology.Panama -> parseFileWithPanama(file.absolutePath) +private fun parseFile( + file: File, + filePath: Path? = null, + headerPaths: Array = arrayOf(), + parserTechnology: ParserTechnology = ParserTechnology.Panama +) = when (parserTechnology) { + ParserTechnology.JNA -> { + assert(filePath == null) { "file path is not supported on JNA" } + assert(headerPaths.isEmpty()) { "header paths is not supported on JNA" } + parseFileWithJna(file.absolutePath) + } + ParserTechnology.Panama -> parseFileWithPanama(file.absolutePath, filePath, headerPaths) } \ No newline at end of file diff --git a/klang/klang/src/main/kotlin/klang/parser/libclang/PanamaLibclangParser.kt b/klang/klang/src/main/kotlin/klang/parser/libclang/PanamaLibclangParser.kt index 014eae26..f0fc5c0c 100644 --- a/klang/klang/src/main/kotlin/klang/parser/libclang/PanamaLibclangParser.kt +++ b/klang/klang/src/main/kotlin/klang/parser/libclang/PanamaLibclangParser.kt @@ -20,13 +20,17 @@ import java.nio.file.Paths private val logger = KotlinLogging.logger {} -fun parseFileWithPanama(file: String): DeclarationRepository = InMemoryDeclarationRepository().apply { +fun parseFileWithPanama(file: String, filePath: Path?, headerPaths: Array): DeclarationRepository = InMemoryDeclarationRepository().apply { val header = Path.of(file) - val clangArguments = inferPlatformIncludePath() + var clangArguments = inferPlatformIncludePath() ?.let { "-I$it" } ?.let { arrayOf(it) } ?: arrayOf() + clangArguments += filePath?.let { "-I${it.toFile().absolutePath}" } + ?.let { arrayOf(it) } + ?: arrayOf() + clangArguments += headerPaths.map { "-I${it.toFile().absolutePath}" } val topLevel = parse( listOf(header), diff --git a/klang/klang/src/test/c/c-headers.zip b/klang/klang/src/test/c/c-headers.zip new file mode 100644 index 00000000..228df652 Binary files /dev/null and b/klang/klang/src/test/c/c-headers.zip differ diff --git a/klang/klang/src/test/kotlin/klang/parser/libclang/SDL2ItTest.kt b/klang/klang/src/test/kotlin/klang/parser/libclang/SDL2ItTest.kt new file mode 100644 index 00000000..9d1e1771 --- /dev/null +++ b/klang/klang/src/test/kotlin/klang/parser/libclang/SDL2ItTest.kt @@ -0,0 +1,26 @@ +package klang.parser.libclang + +import klang.parser.INTEGRATION_ENABLED +import klang.parser.ParserTestCommon + + +class SDL2ItTest : ParserTestCommon({ + + "test SDL2 parsing".config(enabled = INTEGRATION_ENABLED || true) { + + // Given + val filePath = "src/test/c/" + val fileToParse = "SDL2/SDL.h" + val headerPaths = arrayOf("src/test/c/c/include") + + // When + val repository = parseFile(fileToParse, filePath, headerPaths) + + // Then + repository.apply { + println(declarations.size) + } + + + } +}) \ No newline at end of file