C Compiler written in Kotlin + Small web-based Editor with autocompletion
Branch: master
Clone or download
Fetching latest commit…
Cannot retrieve the latest commit at this time.
Permalink
Type Name Latest commit message Commit time
Failed to load latest commit information.
@old
doc Add annex-b Jan 24, 2019
docs We cannot use `@JvmName` on unsigned types, but we can do it in the s… Jan 29, 2019
gradle/wrapper More work Jan 19, 2019
samples More work Jan 25, 2019
src
.gitignore More work Jan 25, 2019
.travis.yml 0.6.0 Jan 25, 2019
Dockerfile Update building docker image to Kotlin 1.3.20 Jan 23, 2019
LICENSE
README.md Update README.md Jan 25, 2019
build.gradle.kts Small adjustments Jan 28, 2019
build.gradle.old Try using Kotlin for build-script Jan 23, 2019
build_docker_image.sh
build_docker_image_and_publish.sh
gradle.properties 0.6.0 Jan 25, 2019
gradlew More work Jan 19, 2019
gradlew.bat More work Jan 19, 2019
gradlew_linux Support goto with a state machine lowering, (switch + for) now are ha… Jan 22, 2019
gradlew_win Support goto with a state machine lowering, (switch + for) now are ha… Jan 22, 2019
gradlew_wine Update multiplatform gradle wrappers to latest version Jan 20, 2019
ktcc Some docker work Jan 21, 2019
ktcc_jvm Small adjustments Jan 22, 2019
ktcc_jvm_integration_test More work Jan 24, 2019
linux Support goto with a state machine lowering, (switch + for) now are ha… Jan 22, 2019
settings.gradle.kts Prepare for a future serialization using kotlinx.serializer (at the m… Jan 28, 2019
settings.gradle.old Try using Kotlin for build-script Jan 23, 2019
testJs.sh Kotlin 1.3.20 + new testJs.sh that do not hang processes + fixed prep… Jan 23, 2019
win Support goto with a state machine lowering, (switch + for) now are ha… Jan 22, 2019
win_cmd

README.md

ktcc

A C Compiler written in Multiplatform Kotlin (JVM, JS and Native).

Online live editor (Video)

It aims to generate Kotlin and potentially other targets from ANSI C code.

Use cases:

  • Compile C libraries into multiplatform Kotlin projects (that works on the JVM, JS and Native)
  • Convert C libraries into logical Kotlin code that can be modified

Using:

  • Provided as JVM library and CLI tool.
  • Provided as native executable (linux, mac and windows).
  • Provided as docker image with the compiler native executable. Just run latest uploaded version with: docker run --rm "-v$PWD:/data" soywiz/ktcc $*
  • Provided as JavaScript library and pure client-side online service. It autocompletes and generates Kotlin code on the fly on your browser.

CLI usage:

./gradlew fatJar
java -jar build/libs/ktcc-all.jar samples/simple.c      # outputs the kotlin code

Compile the c compiler with kotlin-native as a executable without dependencies:

./gradlew linkRelease
./build/bin/macosX64/main/release/executable/ktcc.kexe samples/simple.c

Cross-compile the compiler native executable for windows or linux in a mac machine (requires docker):

./gradlew_linux linkReleaseExecutableLinuxX64 # linux
./gradlew_win linkReleaseExecutableMingwX64   # windows

Compile the docker image:

./build_docker_image.sh

Ideas

Handling structs with inline classes

While keeping the code using structures sane.

fun alloca(size: Int): CPointer<Unit> = CPointer<Unit>((STACK_PTR - size).also { STACK_PTR -= size })

inline fun <T> stackFrame(callback: () -> T): T {
    val oldPos = STACK_PTR
    return try { callback() } finally { STACK_PTR = oldPos }
}

inline class MyStruct2(val ptr: Int) {
    companion object {
        val SIZEOF = 4
        val OFFSET_a = 0
    }
    var a: Int get() = lw(ptr + OFFSET_a); set(value) = run { sw(ptr + OFFSET_a, value) }
}

inline class MyStruct(val ptr: Int) {
    companion object {
        val SIZEOF = 12
        val OFFSET_a = 0
        val OFFSET_b = 4
        val OFFSET_c = 8
    }
    var a: Int get() = lw(ptr + OFFSET_a); set(value) = run { sw(ptr + OFFSET_a, value) }
    var b: MyStruct2 get() = MyStruct2(lw(ptr + OFFSET_b)); set(value) = run { sw(ptr + OFFSET_b, value.ptr) } // Pointer to MyStruct2
    val c: MyStruct2 get() = MyStruct2(ptr + OFFSET_c); set(value) = run { /* memcpy */ }
}

/////////////

fun test() = stackFrame {
    val ms = MyStruct(alloca(MyStruct.SIZEOF)) 
    ms.b = MyStruct2(10)
    ms.b.a = 10
}