Skip to content

Commit

Permalink
Drastic shader loading improvements
Browse files Browse the repository at this point in the history
  • Loading branch information
IMS212 committed Oct 1, 2024
1 parent 4f28e9e commit b4e0e10
Show file tree
Hide file tree
Showing 15 changed files with 196 additions and 74 deletions.
4 changes: 2 additions & 2 deletions build.gradle.kts
Original file line number Diff line number Diff line change
Expand Up @@ -4,10 +4,10 @@ plugins {
id("fabric-loom") version("1.7.2") apply(false)
}

val MINECRAFT_VERSION by extra { "24w38a" }
val MINECRAFT_VERSION by extra { "24w39a" }
val NEOFORGE_VERSION by extra { "21.1.19" }
val FABRIC_LOADER_VERSION by extra { "0.16.5" }
val FABRIC_API_VERSION by extra { "0.104.2+1.21.2" }
val FABRIC_API_VERSION by extra { "0.105.1+1.21.2" }
val SODIUM_FILE by extra { "sodium-fabric-0.6.0-snapshot+mc24w38a-local.jar" }

// https://semver.org/
Expand Down
9 changes: 9 additions & 0 deletions common/src/main/java/net/irisshaders/iris/Iris.java
Original file line number Diff line number Diff line change
Expand Up @@ -45,6 +45,9 @@
import net.minecraft.network.chat.HoverEvent;
import org.jetbrains.annotations.NotNull;
import org.lwjgl.glfw.GLFW;
import org.lwjgl.opengl.ARBParallelShaderCompile;
import org.lwjgl.opengl.GL;
import org.lwjgl.opengl.KHRParallelShaderCompile;

import java.io.IOException;
import java.io.InputStream;
Expand Down Expand Up @@ -116,6 +119,12 @@ public static void onRenderSystemInit() {
return;
}

if (GL.getCapabilities().GL_KHR_parallel_shader_compile) {
KHRParallelShaderCompile.glMaxShaderCompilerThreadsKHR(10);
} else if (GL.getCapabilities().GL_ARB_parallel_shader_compile) {
ARBParallelShaderCompile.glMaxShaderCompilerThreadsARB(10);
}

PBRTextureManager.INSTANCE.init();

VertexSerializerRegistry.instance().registerSerializer(DefaultVertexFormat.NEW_ENTITY, IrisVertexFormats.TERRAIN, new EntityToTerrainVertexSerializer());
Expand Down
10 changes: 10 additions & 0 deletions common/src/main/java/net/irisshaders/iris/helpers/Tri.java
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,16 @@ public boolean equals(Object obj) {
return tri.first == this.first && tri.second == this.second && tri.third == this.third;
}

@Override
public int hashCode() {
final int prime = 31;
int result = 1;
result = prime * result + ((first == null) ? 0 : first.hashCode());
result = prime * result + ((second == null) ? 0 : second.hashCode());
result = prime * result + ((third == null) ? 0 : third.hashCode());
return result;
}

@Override
public String toString() {
return "First: " + first.toString() + " Second: " + second.toString() + " Third: " + third.toString();
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -100,6 +100,7 @@ public class MixinLevelRenderer {

if (pipeline.shouldDisableFrustumCulling()) {
this.cullingFrustum = new NonCullingFrustum();
this.cullingFrustum.prepare(camera.getPosition().x(), camera.getPosition().y(), camera.getPosition().z());
}
pipeline.beginLevelRendering();
pipeline.setPhase(WorldRenderingPhase.NONE);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -50,7 +50,9 @@
import net.irisshaders.iris.pipeline.programs.FallbackShader;
import net.irisshaders.iris.pipeline.programs.ShaderCreator;
import net.irisshaders.iris.pipeline.programs.ShaderKey;
import net.irisshaders.iris.pipeline.programs.ShaderLoadingMap;
import net.irisshaders.iris.pipeline.programs.ShaderMap;
import net.irisshaders.iris.pipeline.programs.ShaderSupplier;
import net.irisshaders.iris.pipeline.programs.SodiumPrograms;
import net.irisshaders.iris.pipeline.transform.PatchShaderType;
import net.irisshaders.iris.pipeline.transform.ShaderPrinter;
Expand Down Expand Up @@ -382,7 +384,7 @@ public IrisRenderingPipeline(ProgramSet programSet) {
this.loadedShaders = new HashSet<>();


this.shaderMap = new ShaderMap(key -> {
ShaderLoadingMap loadingMap = new ShaderLoadingMap(key -> {
try {
if (key.isShadow()) {
if (shadowRenderTargets != null) {
Expand All @@ -405,6 +407,8 @@ public IrisRenderingPipeline(ProgramSet programSet) {
}
});

this.shaderMap = new ShaderMap(loadingMap, loadedShaders::add);

initializedBlockIds = false;

WorldRenderingSettings.INSTANCE.setEntityIds(programSet.getPack().getIdMap().getEntityIdMap());
Expand Down Expand Up @@ -628,7 +632,7 @@ private ComputeProgram[] createSetupComputes(ComputeSource[] compute, ProgramSet
return programs;
}

private CompiledShaderProgram createShader(String name, Optional<ProgramSource> source, ShaderKey key) throws IOException {
private ShaderSupplier createShader(String name, Optional<ProgramSource> source, ShaderKey key) throws IOException {
if (source.isEmpty()) {
return createFallbackShader(name, key);
}
Expand All @@ -642,7 +646,7 @@ public Object2ObjectMap<Tri<String, TextureType, TextureStage>, String> getTextu
return customTextureMap;
}

private CompiledShaderProgram createShader(String name, ProgramSource source, ProgramId programId, AlphaTest fallbackAlpha,
private ShaderSupplier createShader(String name, ProgramSource source, ProgramId programId, AlphaTest fallbackAlpha,
VertexFormat vertexFormat, FogMode fogMode,
boolean isIntensity, boolean isFullbright, boolean isGlint, boolean isText, boolean isIE) throws IOException {
GlFramebuffer beforeTranslucent = renderTargets.createGbufferFramebuffer(flippedAfterPrepare, source.getDirectives().getDrawBuffers());
Expand All @@ -656,28 +660,24 @@ private CompiledShaderProgram createShader(String name, ProgramSource source, Pr
() -> isBeforeTranslucent ? flippedAfterPrepare : flippedAfterTranslucent;


ExtendedShader extendedShader = ShaderCreator.create(this, name, source, programId, beforeTranslucent, afterTranslucent,
ShaderSupplier extendedShader = ShaderCreator.create(this, name, source, programId, beforeTranslucent, afterTranslucent,
fallbackAlpha, vertexFormat, inputs, updateNotifier, this, flipped, fogMode, isIntensity, isFullbright, false, isLines, customUniforms);

loadedShaders.add(extendedShader);

return extendedShader;
}

private CompiledShaderProgram createFallbackShader(String name, ShaderKey key) throws IOException {
private ShaderSupplier createFallbackShader(String name, ShaderKey key) throws IOException {
GlFramebuffer beforeTranslucent = renderTargets.createGbufferFramebuffer(flippedAfterPrepare, new int[]{0});
GlFramebuffer afterTranslucent = renderTargets.createGbufferFramebuffer(flippedAfterTranslucent, new int[]{0});

FallbackShader shader = ShaderCreator.createFallback(name, beforeTranslucent, afterTranslucent,
ShaderSupplier shader = ShaderCreator.createFallback(name, beforeTranslucent, afterTranslucent,
key.getAlphaTest(), key.getVertexFormat(), null, this, key.getFogMode(),
key == ShaderKey.GLINT, key.isText(), key.hasDiffuseLighting(), key.isIntensity(), key.shouldIgnoreLightmap());

loadedShaders.add(shader);

return shader;
}

private CompiledShaderProgram createShadowShader(String name, Optional<ProgramSource> source, ShaderKey key) throws IOException {
private ShaderSupplier createShadowShader(String name, Optional<ProgramSource> source, ShaderKey key) throws IOException {
if (source.isEmpty()) {
return createFallbackShadowShader(name, key);
}
Expand All @@ -686,19 +686,17 @@ private CompiledShaderProgram createShadowShader(String name, Optional<ProgramSo
key.isIntensity(), key.shouldIgnoreLightmap(), key.isText(), key == ShaderKey.IE_COMPAT_SHADOW);
}

private CompiledShaderProgram createFallbackShadowShader(String name, ShaderKey key) throws IOException {
private ShaderSupplier createFallbackShadowShader(String name, ShaderKey key) throws IOException {
GlFramebuffer framebuffer = shadowRenderTargets.createShadowFramebuffer(ImmutableSet.of(), new int[]{0});

FallbackShader shader = ShaderCreator.createFallback(name, framebuffer, framebuffer,
ShaderSupplier shader = ShaderCreator.createFallback(name, framebuffer, framebuffer,
key.getAlphaTest(), key.getVertexFormat(), BlendModeOverride.OFF, this, key.getFogMode(),
key == ShaderKey.GLINT, key.isText(), key.hasDiffuseLighting(), key.isIntensity(), key.shouldIgnoreLightmap());

loadedShaders.add(shader);

return shader;
}

private CompiledShaderProgram createShadowShader(String name, ProgramSource source, ProgramId programId, AlphaTest fallbackAlpha,
private ShaderSupplier createShadowShader(String name, ProgramSource source, ProgramId programId, AlphaTest fallbackAlpha,
VertexFormat vertexFormat, boolean isIntensity, boolean isFullbright, boolean isText, boolean isIE) throws IOException {
GlFramebuffer framebuffer = shadowRenderTargets.createShadowFramebuffer(ImmutableSet.of(), source.getDirectives().hasUnknownDrawBuffers() ? new int[]{0, 1} : source.getDirectives().getDrawBuffers());
boolean isLines = programId == ProgramId.Line && resolver.has(ProgramId.Line);
Expand All @@ -707,11 +705,9 @@ private CompiledShaderProgram createShadowShader(String name, ProgramSource sour

Supplier<ImmutableSet<Integer>> flipped = () -> flippedBeforeShadow;

ExtendedShader extendedShader = ShaderCreator.create(this, name, source, programId, framebuffer, framebuffer,
ShaderSupplier extendedShader = ShaderCreator.create(this, name, source, programId, framebuffer, framebuffer,
fallbackAlpha, vertexFormat, inputs, updateNotifier, this, flipped, FogMode.PER_VERTEX, isIntensity, isFullbright, true, isLines, customUniforms);

loadedShaders.add(extendedShader);

return extendedShader;
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -151,10 +151,7 @@ public void clear() {
public void apply() {
CapturedRenderingState.INSTANCE.setCurrentAlphaTest(alphaTest);

if (lastApplied != this) {
lastApplied = this;
GlStateManager._glUseProgram(getProgramId());
}
GlStateManager._glUseProgram(getProgramId());

int i = GlStateManager._getActiveTexture();

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -60,7 +60,7 @@
import java.util.function.Supplier;

public class ShaderCreator {
public static ExtendedShader create(WorldRenderingPipeline pipeline, String name, ProgramSource source, ProgramId programId, GlFramebuffer writingToBeforeTranslucent,
public static ShaderSupplier create(WorldRenderingPipeline pipeline, String name, ProgramSource source, ProgramId programId, GlFramebuffer writingToBeforeTranslucent,
GlFramebuffer writingToAfterTranslucent, AlphaTest fallbackAlpha,
VertexFormat vertexFormat, ShaderAttributeInputs inputs, FrameUpdateNotifier updateNotifier,
IrisRenderingPipeline parent, Supplier<ImmutableSet<Integer>> flipped, FogMode fogMode, boolean isIntensity,
Expand Down Expand Up @@ -148,14 +148,20 @@ public static ExtendedShader create(WorldRenderingPipeline pipeline, String name
int id = link(name, vertex, geometry, tessControl, tessEval, fragment, vertexFormat);


return new ExtendedShader(id, shaderResourceFactory, name, vertexFormat, tessControl != null || tessEval != null, writingToBeforeTranslucent, writingToAfterTranslucent, blendModeOverride, alpha, uniforms -> {
CommonUniforms.addDynamicUniforms(uniforms, FogMode.PER_VERTEX);
customUniforms.assignTo(uniforms);
BuiltinReplacementUniforms.addBuiltinReplacementUniforms(uniforms);
VanillaUniforms.addVanillaUniforms(uniforms);
}, (samplerHolder, imageHolder) -> {
parent.addGbufferOrShadowSamplers(samplerHolder, imageHolder, flipped, isShadowPass, inputs.hasTex(), inputs.hasLight(), inputs.hasOverlay());
}, isIntensity, parent, overrides, customUniforms);
return new ShaderSupplier(id, () -> {
try {
return new ExtendedShader(id, shaderResourceFactory, name, vertexFormat, tessControl != null || tessEval != null, writingToBeforeTranslucent, writingToAfterTranslucent, blendModeOverride, alpha, uniforms -> {
CommonUniforms.addDynamicUniforms(uniforms, FogMode.PER_VERTEX);
customUniforms.assignTo(uniforms);
BuiltinReplacementUniforms.addBuiltinReplacementUniforms(uniforms);
VanillaUniforms.addVanillaUniforms(uniforms);
}, (samplerHolder, imageHolder) -> {
parent.addGbufferOrShadowSamplers(samplerHolder, imageHolder, flipped, isShadowPass, inputs.hasTex(), inputs.hasLight(), inputs.hasOverlay());
}, isIntensity, parent, overrides, customUniforms);
} catch (IOException e) {
throw new RuntimeException(e);
}
});
}


Expand All @@ -180,21 +186,13 @@ public static int link(String name, String vertex, String geometry, String tessC
((VertexFormatExtension) vertexFormat).bindAttributesIris(i);
GlStateManager.glLinkProgram(i);

int j = GlStateManager.glGetProgrami(i, 35714);
if (j == 0) {
String string = GlStateManager.glGetProgramInfoLog(i, 32768);
throw new ShaderCompileException(
name, string
);
} else {
detachIfValid(i, vertexS);
detachIfValid(i, geometryS);
detachIfValid(i, tessContS);
detachIfValid(i, tessEvalS);
detachIfValid(i, fragS);

return i;
}
}
}

Expand Down Expand Up @@ -232,7 +230,7 @@ private static int createShader(String name, ShaderType shaderType, String sourc
return shader;
}

public static FallbackShader createFallback(String name, GlFramebuffer writingToBeforeTranslucent,
public static ShaderSupplier createFallback(String name, GlFramebuffer writingToBeforeTranslucent,
GlFramebuffer writingToAfterTranslucent, AlphaTest alpha,
VertexFormat vertexFormat, BlendModeOverride blendModeOverride,
IrisRenderingPipeline parent, FogMode fogMode, boolean entityLighting,
Expand Down Expand Up @@ -292,9 +290,17 @@ public static FallbackShader createFallback(String name, GlFramebuffer writingTo

ResourceProvider shaderResourceFactory = new IrisProgramResourceFactory(shaderJsonString, vertex, null, null, null, fragment);

int id = link(name, vertex, null, null, null, fragment, vertexFormat);

// TODO 24w34a FALLBACK
return new FallbackShader(link(name, vertex, null, null, null, fragment, vertexFormat), shaderProgramConfig, shaderResourceFactory, name, vertexFormat, writingToBeforeTranslucent,
writingToAfterTranslucent, blendModeOverride, alpha.reference(), parent);
return new ShaderSupplier(id, () -> {
try {
return new FallbackShader(id, shaderProgramConfig, shaderResourceFactory, name, vertexFormat, writingToBeforeTranslucent,
writingToAfterTranslucent, blendModeOverride, alpha.reference(), parent);
} catch (IOException e) {
throw new RuntimeException(e);
}
});
}

private record IrisProgramResourceFactory(String json, String vertex, String geometry, String tessControl,
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,31 @@
package net.irisshaders.iris.pipeline.programs;

import net.minecraft.client.renderer.CompiledShaderProgram;

import java.util.function.BiConsumer;
import java.util.function.Function;

/**
* A specialized map mapping {@link ShaderKey} to {@link CompiledShaderProgram}.
* Avoids much of the complexity / overhead of an EnumMap while ultimately
* fulfilling the same function.
*/
public class ShaderLoadingMap {
private final ShaderSupplier[] shaders;

public ShaderLoadingMap(Function<ShaderKey, ShaderSupplier> factory) {
ShaderKey[] ids = ShaderKey.values();

this.shaders = new ShaderSupplier[ids.length];

for (int i = 0; i < ids.length; i++) {
this.shaders[i] = factory.apply(ids[i]);
}
}

public void forAllShaders(BiConsumer<ShaderKey, ShaderSupplier> consumer) {
for (int i = 0; i < ShaderKey.values().length; i++) {
consumer.accept(ShaderKey.values()[i], this.shaders[i]);
}
}
}
Original file line number Diff line number Diff line change
@@ -1,7 +1,11 @@
package net.irisshaders.iris.pipeline.programs;

import com.mojang.blaze3d.platform.GlStateManager;
import net.irisshaders.iris.gl.shader.ShaderCompileException;
import net.minecraft.client.renderer.CompiledShaderProgram;
import org.lwjgl.opengl.GL46C;

import java.util.function.Consumer;
import java.util.function.Function;

/**
Expand All @@ -12,13 +16,30 @@
public class ShaderMap {
private final CompiledShaderProgram[] shaders;

public ShaderMap(Function<ShaderKey, CompiledShaderProgram> factory) {
public ShaderMap(ShaderLoadingMap loadingMap, Consumer<CompiledShaderProgram> programConsumer) {
ShaderKey[] ids = ShaderKey.values();

this.shaders = new CompiledShaderProgram[ids.length];

for (int i = 0; i < ids.length; i++) {
this.shaders[i] = factory.apply(ids[i]);
loadingMap.forAllShaders((key, shader) -> {
if (shader != null) {
checkLinkingState(key, shader);
CompiledShaderProgram shaderProgram = shader.shader().get();
this.shaders[key.ordinal()] = shaderProgram;
programConsumer.accept(shaderProgram);
}
});
}

private void checkLinkingState(ShaderKey key, ShaderSupplier shader) {
int i = shader.id();

int j = GlStateManager.glGetProgrami(i, 35714);
if (j == GL46C.GL_FALSE) {
String string = GlStateManager.glGetProgramInfoLog(i, 32768);
throw new ShaderCompileException(
key.name(), string
);
}
}

Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
package net.irisshaders.iris.pipeline.programs;

import net.minecraft.client.renderer.CompiledShaderProgram;

import java.util.function.Supplier;

public record ShaderSupplier(int id, Supplier<CompiledShaderProgram> shader) {
}
Loading

0 comments on commit b4e0e10

Please sign in to comment.