Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
65 commits
Select commit Hold shift + click to select a range
b2029b7
convert to new Scala 3 syntax, fix warnings, restructure test directo…
spamegg1 Jun 16, 2025
524557b
Github Actions should check if code compiles
spamegg1 Jun 16, 2025
0096f76
change job name
spamegg1 Jun 16, 2025
4146222
Merge pull request #49 from ComputeNode/fix-warnings
szymon-rd Jun 16, 2025
903f629
Refactor DSL
szymon-rd Jun 16, 2025
7ddd112
Formatting of refactor
szymon-rd Jun 16, 2025
41267ce
SpirvTools integration (#39)
Soleod Jun 16, 2025
6392ce7
Syntax modernization and cleanup (#52)
Soleod Jun 20, 2025
83e3070
New cyfra core (#53)
szymon-rd Jul 6, 2025
4a93d16
Vulkan cleanup (#57)
MarconZet Jul 7, 2025
b7082cd
Basic Vulkan runtime (#61)
MarconZet Jul 25, 2025
da98629
interpreter
spamegg1 Jul 27, 2025
24678fc
Fs2 interop
spamegg1 Jul 27, 2025
ff40778
redesign and big refactor, finish when simulation
spamegg1 Jul 31, 2025
3f4c515
fix simulate tests
spamegg1 Aug 1, 2025
113bbbe
change design a bit, rename classes better
spamegg1 Aug 1, 2025
37a5291
implement writes in Interpreter
spamegg1 Aug 2, 2025
95e514c
add coalesce write profile, interpreter tests
spamegg1 Aug 4, 2025
4a12a4e
add race condition logic and Idle periods
spamegg1 Aug 9, 2025
db2eb0c
progress on filter: upsweep and downsweep
spamegg1 Aug 12, 2025
386e101
progress on upsweep / downsweep phases
spamegg1 Aug 13, 2025
3ea8eb9
factor out legacy gPipe code
spamegg1 Aug 16, 2025
3094fcb
Improved vulkan stability (#64)
MarconZet Aug 16, 2025
24c333a
outline / sketch compaction and filter, add filter test
spamegg1 Aug 18, 2025
278bbb0
some comments
spamegg1 Aug 20, 2025
c72e45c
GIO and Layouts WIP
szymon-rd Aug 20, 2025
27888dc
WIP2
szymon-rd Aug 23, 2025
21494b8
WIP3
szymon-rd Aug 23, 2025
03fa272
executing, not workin^g
Aug 24, 2025
046a823
add idle profiling
spamegg1 Aug 24, 2025
74d8d8b
Works!
szymon-rd Aug 24, 2025
dbf1734
FlatMap
szymon-rd Aug 24, 2025
b2d53f8
added stream compaction program
spamegg1 Aug 26, 2025
77deb47
finish filter
spamegg1 Aug 26, 2025
dcfe4f9
small fix
spamegg1 Aug 26, 2025
0f92e5d
implement GIO.when and use for-expression in compactProgram
spamegg1 Aug 27, 2025
2840c28
small cleanup
spamegg1 Aug 27, 2025
40aa8e2
more^
Sep 3, 2025
1a01f99
No warnings now
szymon-rd Sep 6, 2025
0177631
Merge branch 'gio-and-layouts' into cyfra-fs2-interop
szymon-rd Sep 6, 2025
c5d7da0
Rebase & adjustments
szymon-rd Sep 7, 2025
aa91317
More adjustments and printf
szymon-rd Sep 7, 2025
6354e42
Works!!!
szymon-rd Sep 7, 2025
a052ba2
Improvements
szymon-rd Sep 8, 2025
62c383c
curret std^
Sep 8, 2025
6993f85
working^
Sep 8, 2025
226c121
todo^
Sep 8, 2025
fdc9ee2
foramt^^
Sep 8, 2025
1ab927a
not working destroy^
Sep 9, 2025
2d75933
working intermediete submission^
Sep 9, 2025
19c0bfe
Various fixes and improvements
szymon-rd Sep 9, 2025
92d0219
fix
Sep 10, 2025
cdb7900
fixes^
Sep 11, 2025
a785aa8
Merge branch 'mzlakowski/lazy-eval' into gio-and-layouts
szymon-rd Sep 11, 2025
dbcae9d
Lazy and concurrent command buffer evaluation (#68)
MarconZet Sep 11, 2025
4eb491e
Progres on porting GFunc
szymon-rd Sep 11, 2025
763c3a5
Old samples work now
szymon-rd Sep 14, 2025
bc26f58
change instance creation^
MarconZet Sep 21, 2025
3172910
fomrating^
MarconZet Sep 21, 2025
34b8e6b
Merge branch 'dev' into gio-and-layouts
MarconZet Sep 21, 2025
1f7a526
fixed filter^
MarconZet Sep 21, 2025
76ff1eb
Fix cache
szymon-rd Oct 19, 2025
6fc37a9
Merge pull request #66 from ComputeNode/gio-and-layouts
szymon-rd Oct 19, 2025
35d428b
Merge branch 'dev' into interpreter
spamegg1 Nov 11, 2025
df5ed99
fix compile errors (tests are still broken)
spamegg1 Nov 11, 2025
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
6 changes: 4 additions & 2 deletions .github/workflows/ci.yml
Original file line number Diff line number Diff line change
Expand Up @@ -6,9 +6,11 @@ on:
tags:
- "v*"
pull_request:
branches:
- dev

jobs:
format:
format_and_compile:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
Expand All @@ -19,4 +21,4 @@ jobs:
with:
jvm: graalvm-java21
apps: sbt
- run: sbt "formatCheckAll"
- run: sbt "formatCheckAll; compile"
1 change: 1 addition & 0 deletions .scalafmt.conf
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@ optIn.configStyleArguments = false
rewrite.rules = [RedundantBraces, RedundantParens, SortModifiers, PreferCurlyFors, Imports]
rewrite.sortModifiers.preset = styleGuide
rewrite.trailingCommas.style = always
rewrite.scala3.convertToNewSyntax = true

indent.defnSite = 2
newlines.inInterpolation = "avoid"
Expand Down
23 changes: 18 additions & 5 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -3,8 +3,10 @@
Library provides a way to compile Scala 3 DSL to SPIR-V and to run it with Vulkan runtime on GPUs.

It is multiplatform. It works on:
- Linux, Windows, and Mac (for Mac requires installation of moltenvk).
- Any dedicated or integrated GPUs that support Vulkan. In practice, it means almost all moderately modern devices from most manufacturers including Nvidia, AMD, Intel, Apple.

- Linux, Windows, and Mac (for Mac requires installation of moltenvk).
- Any dedicated or integrated GPUs that support Vulkan. In practice, it means almost all moderately modern devices from
most manufacturers including Nvidia, AMD, Intel, Apple.

Library is in an early stage - alpha release and proper documentation are coming.

Expand All @@ -15,22 +17,27 @@ Included Foton library provides a clean and fun way to animate functions and ray
## Examples

### Ray traced animation

![output](https://github.com/user-attachments/assets/3eac9f7f-72df-4a5d-b768-9117d651c78d)

[code](https://github.com/ComputeNode/cyfra/blob/50aecea/cyfra-examples/src/main/scala/io/computenode/samples/cyfra/foton/AnimatedRaytrace.scala)
(this is API usage, to see ray tracing implementation look at [RtRenderer](https://github.com/ComputeNode/cyfra/blob/50aecea132188776021afe0b407817665676a021/cyfra-foton/src/main/scala/io/computenode/cyfra/foton/rt/RtRenderer.scala))
(this is API usage, to see ray tracing implementation look
at [RtRenderer](https://github.com/ComputeNode/cyfra/blob/50aecea132188776021afe0b407817665676a021/cyfra-foton/src/main/scala/io/computenode/cyfra/foton/rt/RtRenderer.scala))

### Animated Julia set

<img src="assets/julia.gif" width="360">

[code](https://github.com/ComputeNode/cyfra/blob/50aecea132188776021afe0b407817665676a021/cyfra-examples/src/main/scala/io/computenode/samples/cyfra/foton/AnimatedJulia.scala)

## Animation features examples

### Custom animated functions

<img src="https://github.com/user-attachments/assets/1030d968-014a-4c2c-8f21-26b999fe57fc" width="650">

### Animated ray traced scene

<img src="https://github.com/user-attachments/assets/a4189bc3-e2a9-4e52-9363-93f83b530595" width="750">

## Coding features examples
Expand All @@ -48,9 +55,15 @@ Included Foton library provides a clean and fun way to animate functions and ray

## Development

To enable validation layers for vulkan, you need to install vulkan SKD. After installing, set the following VM options:
To enable validation layers for vulkan, you need to install vulkan SKD. After installing, set the following VM option:

```
-Dorg.lwjgl.vulkan.libname=libvulkan.1.dylib
-Dio.computenode.cyfra.vulkan.validation=true
```

If you are on MacOs, then also add:

```
-Dorg.lwjgl.vulkan.libname=libvulkan.1.dylib
-Djava.library.path=$VULKAN_SDK/lib
```
38 changes: 29 additions & 9 deletions build.sbt
Original file line number Diff line number Diff line change
@@ -1,8 +1,8 @@
ThisBuild / organization := "com.computenode.cyfra"
ThisBuild / scalaVersion := "3.6.4"
ThisBuild / version := "0.1.0-SNAPSHOT"
ThisBuild / version := "0.2.0-SNAPSHOT"

val lwjglVersion = "3.3.6"
val lwjglVersion = "3.4.0-SNAPSHOT"
val jomlVersion = "1.10.0"

lazy val osName = System.getProperty("os.name").toLowerCase
Expand Down Expand Up @@ -36,8 +36,10 @@ lazy val vulkanNatives =
else Seq.empty

lazy val commonSettings = Seq(
scalacOptions ++= Seq("-feature", "-deprecation", "-unchecked", "-language:implicitConversions"),
resolvers += "maven snapshots" at "https://central.sonatype.com/repository/maven-snapshots/",
libraryDependencies ++= Seq(
"dev.zio" % "izumi-reflect_3" % "2.3.10",
"dev.zio" % "izumi-reflect_3" % "3.0.5",
"com.lihaoyi" % "pprint_3" % "0.9.0",
"com.diogonunes" % "JColor" % "5.5.1",
"org.lwjgl" % "lwjgl" % lwjglVersion,
Expand All @@ -47,54 +49,72 @@ lazy val commonSettings = Seq(
"org.lwjgl" % "lwjgl-vma" % lwjglVersion classifier lwjglNatives,
"org.joml" % "joml" % jomlVersion,
"commons-io" % "commons-io" % "2.16.1",
"org.slf4j" % "slf4j-api" % "1.7.30",
"org.slf4j" % "slf4j-simple" % "1.7.30" % Test,
"org.scalameta" % "munit_3" % "1.0.0" % Test,
"com.lihaoyi" %% "sourcecode" % "0.4.3-M5",
"org.slf4j" % "slf4j-api" % "2.0.17",
"org.apache.logging.log4j" % "log4j-slf4j2-impl" % "2.24.3" % Test,
) ++ vulkanNatives,
)

lazy val runnerSettings = Seq(libraryDependencies += "org.apache.logging.log4j" % "log4j-slf4j2-impl" % "2.24.3")

lazy val fs2Settings = Seq(libraryDependencies ++= Seq("co.fs2" %% "fs2-core" % "3.12.0", "co.fs2" %% "fs2-io" % "3.12.0"))

lazy val utility = (project in file("cyfra-utility"))
.settings(commonSettings)

lazy val spirvTools = (project in file("cyfra-spirv-tools"))
.settings(commonSettings)
.dependsOn(utility)

lazy val vulkan = (project in file("cyfra-vulkan"))
.settings(commonSettings)
.dependsOn(utility)

lazy val dsl = (project in file("cyfra-dsl"))
.settings(commonSettings)
.dependsOn(vulkan, utility)
.dependsOn(utility)

lazy val compiler = (project in file("cyfra-compiler"))
.settings(commonSettings)
.dependsOn(dsl, utility)

lazy val core = (project in file("cyfra-core"))
.settings(commonSettings)
.dependsOn(compiler, dsl, utility, spirvTools)

lazy val runtime = (project in file("cyfra-runtime"))
.settings(commonSettings)
.dependsOn(compiler, dsl, vulkan, utility)
.dependsOn(core, vulkan)

lazy val foton = (project in file("cyfra-foton"))
.settings(commonSettings)
.dependsOn(compiler, dsl, runtime, utility)

lazy val examples = (project in file("cyfra-examples"))
.settings(commonSettings, runnerSettings)
.settings(libraryDependencies += "org.scala-lang.modules" % "scala-parallel-collections_3" % "1.2.0")
.dependsOn(foton)

lazy val vscode = (project in file("cyfra-vscode"))
.settings(commonSettings)
.dependsOn(foton)

lazy val interpreter = (project in file("cyfra-interpreter"))
.settings(commonSettings)
.dependsOn(dsl, compiler)

lazy val fs2interop = (project in file("cyfra-fs2"))
.settings(commonSettings, fs2Settings)
.dependsOn(runtime)

lazy val e2eTest = (project in file("cyfra-e2e-test"))
.settings(commonSettings, runnerSettings)
.dependsOn(runtime)
.dependsOn(runtime, fs2interop, interpreter)

lazy val root = (project in file("."))
.settings(name := "Cyfra")
.aggregate(compiler, dsl, foton, runtime, vulkan, examples)
.aggregate(compiler, dsl, foton, core, runtime, vulkan, examples, fs2interop, interpreter)

e2eTest / Test / javaOptions ++= Seq("-Dorg.lwjgl.system.stackSize=1024", "-DuniqueLibraryNames=true")

Expand Down
Original file line number Diff line number Diff line change
@@ -1,20 +1,15 @@
package io.computenode.cyfra.spirv

import io.computenode.cyfra.dsl.Control.Scope
import io.computenode.cyfra.dsl.Expression.{E, FunctionCall}
import io.computenode.cyfra.dsl.Value
import io.computenode.cyfra.dsl.macros.Source
import izumi.reflect.Tag
import io.computenode.cyfra.dsl.Expression.E

import scala.collection.mutable
import scala.quoted.Expr

private[cyfra] object BlockBuilder:

def buildBlock(tree: E[_], providedExprIds: Set[Int] = Set.empty): List[E[_]] =
val allVisited = mutable.Map[Int, E[_]]()
def buildBlock(tree: E[?], providedExprIds: Set[Int] = Set.empty): List[E[?]] =
val allVisited = mutable.Map[Int, E[?]]()
val inDegrees = mutable.Map[Int, Int]().withDefaultValue(0)
val q = mutable.Queue[E[_]]()
val q = mutable.Queue[E[?]]()
q.enqueue(tree)
allVisited(tree.treeid) = tree

Expand All @@ -28,8 +23,8 @@ private[cyfra] object BlockBuilder:
allVisited(childId) = child
q.enqueue(child)

val l = mutable.ListBuffer[E[_]]()
val roots = mutable.Queue[E[_]]()
val l = mutable.ListBuffer[E[?]]()
val roots = mutable.Queue[E[?]]()
allVisited.values.foreach: node =>
if inDegrees(node.treeid) == 0 then roots.enqueue(node)

Expand Down
Original file line number Diff line number Diff line change
@@ -1,9 +1,9 @@
package io.computenode.cyfra.spirv

import io.computenode.cyfra.dsl.binding.{GBuffer, GUniform}
import io.computenode.cyfra.dsl.macros.FnCall.FnIdentifier
import io.computenode.cyfra.dsl.macros.Source
import io.computenode.cyfra.spirv.compilers.FunctionCompiler.SprivFunction
import io.computenode.cyfra.spirv.SpirvConstants.HEADER_REFS_TOP
import io.computenode.cyfra.spirv.compilers.FunctionCompiler.SprivFunction
import io.computenode.cyfra.spirv.compilers.SpirvProgramCompiler.ArrayBufferBlock
import izumi.reflect.Tag
import izumi.reflect.macrortti.LightTypeTag
Expand All @@ -17,16 +17,17 @@ private[cyfra] case class Context(
voidTypeRef: Int = -1,
voidFuncTypeRef: Int = -1,
workerIndexRef: Int = -1,
uniformVarRef: Int = -1,
constRefs: Map[(Tag[_], Any), Int] = Map(),
uniformVarRefs: Map[GUniform[?], Int] = Map.empty,
bindingToStructType: Map[Int, Int] = Map.empty,
constRefs: Map[(Tag[?], Any), Int] = Map(),
exprRefs: Map[Int, Int] = Map(),
inBufferBlocks: List[ArrayBufferBlock] = List(),
outBufferBlocks: List[ArrayBufferBlock] = List(),
bufferBlocks: Map[GBuffer[?], ArrayBufferBlock] = Map(),
nextResultId: Int = HEADER_REFS_TOP,
nextBinding: Int = 0,
exprNames: Map[Int, String] = Map(),
memberNames: Map[Int, String] = Map(),
names: Set[String] = Set(),
functions: Map[FnIdentifier, SprivFunction] = Map(),
stringLiterals: Map[String, Int] = Map(),
):
def joinNested(ctx: Context): Context =
this.copy(nextResultId = ctx.nextResultId, exprNames = ctx.exprNames ++ this.exprNames, functions = ctx.functions ++ this.functions)
Expand Down
Loading