Created
February 8, 2020 21:33
-
-
Save kavan-mevada/c5fac73f0c4289741d35e082ae97059d to your computer and use it in GitHub Desktop.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import kotlinx.cinterop.* | |
import platform.posix.* | |
// IrFile | |
// ------------------------------------------------------ | |
data class PsiFile internal constructor(val path: String, var name: String = path.substringAfterLast('/')) | |
val PsiFile.open get() = open(path, O_RDONLY) | |
val PsiFile.size get() = nativeHeap.alloc<stat>().apply { stat(path, ptr) }.st_size | |
// Extension ----------------- | |
fun PsiFile.readUtf8() = run { | |
val fd = open; val size = size | |
mmap(NULL, size.convert(), PROT_READ, MAP_PRIVATE, fd, 0)?.readBytes(size.convert()) | |
?.toKString() ?: throw Exception("Error reading lock file.") | |
} // ---------------------------------------------------- | |
fun PsiFile.rawLoop(exe: (Byte) -> Unit) { | |
val fd = open; val size = size | |
val pointer = mmap(NULL, size.convert(), PROT_READ, MAP_PRIVATE, fd, 0) | |
pointer?.reinterpret<ByteVar>()?.pointed?.ptr?.let { src -> | |
var index = 0 | |
while (index < size) { | |
exe(src[index]) | |
++index | |
} | |
} | |
} | |
fun PsiFile.charLoop(exe: (Char) -> Unit) = rawLoop { exe(it.toChar()) } | |
//----------------------------------------------------------- | |
class PsiBuilder(val psiFile: PsiFile) { | |
val fd = psiFile.open | |
val size = psiFile.size | |
private val pointer = | |
mmap(NULL, size.convert(), PROT_READ, MAP_PRIVATE, fd, 0) | |
?.reinterpret<ByteVar>()?.pointed?.ptr | |
var marker = 0 | |
var nChar: Char? = null | |
var pChar: Char? = ' ' | |
val isEnd get() = if (marker>=size) true else false | |
fun nextChar(): Char? { | |
val c = pointer?.get(marker)?.toChar() | |
return nChar?.let { nChar.apply { nChar=null } } ?: | |
when { // Run this if nextChar is null | |
(pChar ==' ' && c ==' ') || c == '\r' || c == '\n' || c == '\t' -> null | |
// Add space both side these characters | |
pChar !=' ' && c == ',' -> { nChar = ','; ' ' } | |
pChar ==',' && c != ' ' -> { nChar = c; ' ' } | |
pChar !=' ' && c == ':' -> { nChar = ':'; ' ' } | |
pChar ==':' && c != ' ' -> { nChar = c; ' ' } | |
pChar !=' ' && c == '=' -> { nChar = '='; ' ' } | |
pChar =='=' && c != ' ' -> { nChar = c; ' ' } | |
pChar !=' ' && c == '!' -> { nChar = '!'; ' ' } | |
pChar =='!' && c != ' ' -> { nChar = c; ' ' } | |
pChar !=' ' && c == '/' -> { nChar = '/'; ' ' } | |
pChar =='/' && c != ' ' -> { nChar = c; ' ' } | |
pChar !=' ' && c == '{' -> { nChar = '{'; ' ' } | |
pChar =='{' && c != ' ' -> { nChar = c; ' ' } | |
pChar !=' ' && c == '}' -> { nChar = '}'; ' ' } | |
pChar =='}' && c != ' ' -> { nChar = c; ' ' } | |
pChar !=' ' && c == ';' -> { nChar = ';'; ' ' } | |
pChar ==';' && c != ' ' -> { nChar = c; ' ' } | |
pChar !=' ' && c == '(' -> { nChar = '('; ' ' } | |
pChar =='(' && c != ' ' -> { nChar = c; ' ' } | |
pChar !=' ' && c == ')' -> { nChar = ')'; ' ' } | |
pChar ==')' && c != ' ' -> { nChar = c; ' ' } | |
pChar !=' ' && c == '.' -> { nChar = '.'; ' ' } | |
pChar =='.' && c != ' ' -> { nChar = c; ' ' } | |
else -> c | |
}.apply { marker++ /* Go to next marker if nextChar printed */ }.apply { | |
pChar = c // update previous character | |
} | |
} | |
fun nextIterator(): Char? = nextChar() ?: nextIterator() | |
fun nextWord() : String? { | |
var word = "" | |
do { | |
val c = nextIterator() | |
if (c != ' ') word+=c | |
} while (c != ' ' && !isEnd) | |
return if (word=="" && !isEnd) nextWord() else word | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment