public void AddCompiledShader(ShaderCompilationTarget target, List <string> dependencyPaths, CompilationResult result) { string[] defines = new string[target.ShaderMacros.Length]; for (int i = 0; i < target.ShaderMacros.Length; ++i) { defines[i] = target.ShaderMacros[i].Name; } var sourceShader = new SourceShader { Name = target.Path + target.Stage.Extension, Defines = defines }; lock (CompiledShaders) { CompiledShaders[sourceShader] = result; TimeStamps[target.Path] = target.CurrentTimeStamp; foreach (var dependency in dependencyPaths) { TimeStamps[dependency] = File.GetLastWriteTime(dependency).Ticks; } if (!Dependencies.TryGetValue(target.Path, out HashSet <string> cacheDependencyPaths)) { cacheDependencyPaths = new HashSet <string>(); Dependencies.Add(target.Path, cacheDependencyPaths); } foreach (var dependencyPath in dependencyPaths) { cacheDependencyPaths.Add(dependencyPath); } } }
public ShaderRegisters(SourceShader source, string techniqueName, Platform platform) { AsmTechnique technique = source.GetAsmTechnique(techniqueName, platform); vsReg = technique.VertexShader.RegisterSet; psReg = technique.PixelShader.RegisterSet; if (technique.VertexPreShader != null) { vsPreReg = technique.VertexPreShader.RegisterSet; } if (technique.PixelPreShader != null) { psPreReg = technique.PixelPreShader.RegisterSet; } staticArrays = new Dictionary <string, CodeExpression>(); if (technique.TechniqueExtraData != null) { this.techniqueData = technique.TechniqueExtraData; psDefault = technique.TechniqueExtraData.PixelShaderConstants; vsDefault = technique.TechniqueExtraData.VertexShaderConstants; psBooleanDefault = technique.TechniqueExtraData.PixelShaderBooleanConstants; vsBooleanDefault = technique.TechniqueExtraData.VertexShaderBooleanConstants; } }
public SourceDom(SourceShader shader, string baseNamespace, CodeDomProvider provider) { this.codeProvider = provider; this.directives = new CompileDirectives(provider); this.source = shader; this.baseNamespace = baseNamespace; string namespaceName = baseNamespace; if (!shader.UseParentNamespace) { namespaceName += "." + Common.ToUpper(Path.GetFileNameWithoutExtension(source.FileName)); } this.outputNamespace = namespaceName; HlslTechnique[] techniques = shader.GetAllTechniques(); if (shader.DefinePlatform) { //create a copy for each platform //xbox first this.rootPcNamespace = new CodeNamespace(namespaceName); this.rootXboxNamespace = new CodeNamespace(namespaceName); for (int i = 0; i < techniques.Length; i++) { //build the PC shaders if ((techniques[i].Platform & Platform.Windows) == Platform.Windows) { ShaderDom dom = new ShaderDom(source, techniques[i].Name, Platform.Windows, directives); this.rootPcNamespace.Types.Add(dom.CodeTypeDeclaration); } } for (int i = 0; i < techniques.Length; i++) { //build the xbox shaders if ((techniques[i].Platform & Platform.Xbox) == Platform.Xbox) { ShaderDom dom = new ShaderDom(source, techniques[i].Name, Platform.Xbox, directives); this.rootXboxNamespace.Types.Add(dom.CodeTypeDeclaration); } } } else { this.rootNamespace = new CodeNamespace(namespaceName); for (int i = 0; i < techniques.Length; i++) { //build the combined pc / xbox shaders if ((techniques[i].Platform & Platform.Both) == Platform.Both) { ShaderDom dom = new ShaderDom(source, techniques[i].Name, Platform.Both, directives); this.rootNamespace.Types.Add(dom.CodeTypeDeclaration); } } } }
public ShaderBytes(SourceShader source, string techniqueName, Platform platform) { this.source = source; this.platform = platform; this.asmTechnique = source.GetAsmTechnique(techniqueName, platform); this.hlslTechnique = source.GetTechnique(techniqueName, platform); }
public ConstantSetup(SourceShader source, string techniqueName, Platform platform) { this.source = source; this.techniqueName = techniqueName; this.attributeNames = new List <string>(); this.attributeFields = new List <CodeFieldReferenceExpression>(); this.attributeArrayFields = new List <CodeFieldReferenceExpression>(); this.attributeAssignment = new Dictionary <Type, List <CodeStatement> >(); this.semanticMapping = new List <SemanticMapping>(); this.globals = new List <GlobalAttribute>(); this.asm = source.GetAsmTechnique(techniqueName, platform); ComputeAllValidSemantics(); }
public Preshaders(SourceShader source, string techniqueName, Platform platform) { technique = source.GetAsmTechnique(techniqueName, platform); if (technique.PixelPreShader != null) { pixelPreShaderStatements = new CodeStatementCollection(); pixelPreShader = new PreshaderSrc(technique.PixelPreShader, pixelPreShaderStatements); technique.PixelShader.RegisterSet.SetMinFloatRegisterCount(pixelPreShader.MaxConstantRegisterAccess); technique.PixelShader.RegisterSet.SetMinBooleanRegisterCount(pixelPreShader.MaxBooleanConstantRegisterWrite); } if (technique.VertexPreShader != null) { vertexPreShaderStatements = new CodeStatementCollection(); vertexPreShader = new PreshaderSrc(technique.VertexPreShader, vertexPreShaderStatements); technique.VertexShader.RegisterSet.SetMinFloatRegisterCount(vertexPreShader.MaxConstantRegisterAccess); technique.VertexShader.RegisterSet.SetMinBooleanRegisterCount(vertexPreShader.MaxBooleanConstantRegisterWrite); } }
public ShaderTextures(SourceShader source, string techniqueName, Platform platform) { this.psSamplers = new List <Register>(); this.vsSamplers = new List <Register>(); this.allSamplers = new Dictionary <string, SharedSampler>(); AsmTechnique technique = source.GetAsmTechnique(techniqueName, platform); TechniqueExtraData extras = technique.TechniqueExtraData; //pull out the textures that will be used textures = new TextureAssociation[extras.TechniqueTextures.Length]; for (int i = 0; i < extras.TechniqueTextures.Length; i++) { textures[i] = new TextureAssociation(extras.TechniqueTextures[i]); } //now do the samplers RegisterSet set = technique.PixelShader.RegisterSet; //pixel first foreach (Register reg in set) { if (reg.Category == RegisterCategory.Sampler) { psSamplers.Add(reg); int textureIndex = extras.PixelSamplerTextureIndex[reg.Index]; if (textureIndex == -1) { ThrowSamplerNoTextureException(reg); } textures[textureIndex].PsSamplers.Add(reg.Index); //add the sampler to 'allSamplers' SharedSampler ss = new SharedSampler(); ss.PsIndex = reg.Index; ss.SamplerDetails = reg; ss.Index = allSamplers.Count; ss.DefaultState = extras.PixelSamplerStates[reg.Index]; allSamplers.Add(reg.Name, ss); } } set = technique.VertexShader.RegisterSet; //now vertex foreach (Register reg in set) { if (reg.Category == RegisterCategory.Sampler) { vsSamplers.Add(reg); int textureIndex = extras.VertexSamplerTextureIndex[reg.Index]; if (textureIndex == -1) { ThrowSamplerNoTextureException(reg); } textures[textureIndex].VsSamplers.Add(reg.Index); //add the sampler to 'allSamplers' SharedSampler ss; if (!allSamplers.TryGetValue(reg.Name, out ss)) { ss = new SharedSampler(); ss.SamplerDetails = reg; ss.Index = allSamplers.Count; ss.DefaultState = extras.VertexSamplerStates[reg.Index]; allSamplers.Add(reg.Name, ss); } ss.VsIndex = reg.Index; } } }
public static bool TryLoad(Stream stream, out ShaderCompilationCache cache) { using (var reader = new BinaryReader(stream)) { try { cache = new ShaderCompilationCache((ShaderFlags)reader.ReadInt32()); byte[] data = new byte[16384]; var shaderDataCount = reader.ReadInt32(); for (int i = 0; i < shaderDataCount; ++i) { var shaderSource = SourceShader.Read(reader); //Read the size in bytes of the content element data itself. int sizeInBytes = reader.ReadInt32(); if (data.Length < sizeInBytes) { data = new byte[sizeInBytes]; } reader.Read(data, 0, sizeInBytes); ShaderBytecode bytecode; unsafe { fixed(byte *buffer = data) { bytecode = new ShaderBytecode(new IntPtr(buffer), sizeInBytes); } } cache.CompiledShaders.Add(shaderSource, bytecode); } var timeStampCount = reader.ReadInt32(); for (int i = 0; i < timeStampCount; ++i) { var shaderSource = reader.ReadString(); //Read the time stamp. long timeStamp = reader.ReadInt64(); cache.TimeStamps.Add(shaderSource, timeStamp); } var dependenciesCount = reader.ReadInt32(); for (int i = 0; i < dependenciesCount; ++i) { var shaderSource = reader.ReadString(); var pathDependenciesCount = reader.ReadInt32(); var dependencies = new HashSet <string>(); for (int j = 0; j < pathDependenciesCount; ++j) { dependencies.Add(reader.ReadString()); } cache.Dependencies.Add(shaderSource, dependencies); } } catch { cache = null; return(false); } return(true); } }
public ShaderDom(SourceShader source, string techniqueName, Platform platform, CompileDirectives directives) { this.domList = new List <DomBase>(); this.domList.Add(this); this.isShaderExtenable = source.GetShaderExtended(techniqueName); this.shaderExtendsFrom = source.GetShaderExtension(techniqueName); //add custom dom's this.domList.Add(new ShaderBytes(source, techniqueName, platform)); if (shaderExtendsFrom == null) { this.domList.Add(new ShaderRegisters(source, techniqueName, platform)); this.domList.Add(new ConstantSetup(source, techniqueName, platform)); this.domList.Add(new ShaderTextures(source, techniqueName, platform)); this.domList.Add(new Preshaders(source, techniqueName, platform)); } foreach (DomBase dom in domList) { dom.Setup(this); } this.techniqueName = techniqueName; this.source = source; this.platform = platform; classDom = new CodeTypeDeclaration(techniqueName); classDom.IsClass = true; classDom.Attributes = MemberAttributes.Final | MemberAttributes.Public; classDom.TypeAttributes = TypeAttributes.Sealed | TypeAttributes.Public | TypeAttributes.Class; //provide a useful comment to the class GenerateClassComment(); if (source.GenerateInternalClass) { classDom.Attributes = MemberAttributes.Final | MemberAttributes.Assembly; classDom.TypeAttributes = TypeAttributes.NestedAssembly | TypeAttributes.Class | TypeAttributes.Sealed; } if (isShaderExtenable) { classDom.Attributes = MemberAttributes.Public; classDom.TypeAttributes = TypeAttributes.Public | TypeAttributes.Class; if (source.GenerateInternalClass) { classDom.Attributes = MemberAttributes.Assembly; classDom.TypeAttributes = TypeAttributes.NestedAssembly | TypeAttributes.Class; } } classDom.CustomAttributes.Add(new CodeAttributeDeclaration(new CodeTypeReference(typeof(System.Diagnostics.DebuggerStepThroughAttribute)))); classDom.CustomAttributes.Add(new CodeAttributeDeclaration(new CodeTypeReference(typeof(System.CodeDom.Compiler.GeneratedCodeAttribute)), new CodeAttributeArgument(new CodePrimitiveExpression(GetType().Assembly.ManifestModule.Name)), new CodeAttributeArgument(new CodePrimitiveExpression(GetType().Assembly.ManifestModule.ModuleVersionId.ToString())))); if (shaderExtendsFrom != null) { classDom.BaseTypes.Add(new CodeTypeReference(shaderExtendsFrom)); } else { classDom.BaseTypes.Add(new CodeTypeReference(typeof(BaseShader))); } //add custom base types to the shader //these are defined in TechniqueExtraData AsmTechnique asmTechnique = this.source.GetAsmTechnique(this.techniqueName, this.platform); if (asmTechnique.TechniqueExtraData != null && asmTechnique.TechniqueExtraData.ClassBaseTypes != null) { foreach (string baseTypeName in asmTechnique.TechniqueExtraData.ClassBaseTypes) { classDom.BaseTypes.Add(new CodeTypeReference(baseTypeName)); } } this.directives = directives; SetupMembers(techniqueName); foreach (DomBase dom in domList) { dom.SetupMembers(this); } if (shaderExtendsFrom == null) { CreateConstructor(); CreateStaticGraphicsInitMethod(); CreateBindMethod(); } if (shaderExtendsFrom != null || isShaderExtenable) { CreateLocalDeviceIndexProperty(); } CreateWarmShaderMethod(); if (shaderExtendsFrom == null) { CreateChangedMethod(); } CreateVertexInputMethods(); if (shaderExtendsFrom == null) { CreateShaderConstantHashMethod(); } CodeTypeMemberCollection pcMembers = new CodeTypeMemberCollection(); CodeTypeMemberCollection xboxMembers = new CodeTypeMemberCollection(); foreach (DomBase dom in this.domList) { dom.AddMembers(this, delegate(CodeTypeMember s, string c) { Comment(s, c); classDom.Members.Add(s); }, Platform.Both); if (!source.DefinePlatform) // no need for specialization when the platform is constant { dom.AddMembers(this, delegate(CodeTypeMember s, string c) { Comment(s, c); pcMembers.Add(s); }, Platform.Windows); dom.AddMembers(this, delegate(CodeTypeMember s, string c) { Comment(s, c); xboxMembers.Add(s); }, Platform.Xbox); } } foreach (DomBase dom in this.domList) { dom.AddReadonlyMembers(this, delegate(CodeTypeMember s, string c) { CodeTypeMember readonlySnip = directives.CreateReadOnlySnippet(); Comment(readonlySnip ?? s, c); if (readonlySnip != null) { classDom.Members.Add(readonlySnip); } classDom.Members.Add(s); }, Platform.Both); if (!source.DefinePlatform) { dom.AddReadonlyMembers(this, delegate(CodeTypeMember s, string c) { CodeTypeMember readonlySnip = directives.CreateReadOnlySnippet(); Comment(readonlySnip ?? s, c); if (readonlySnip != null) { pcMembers.Add(readonlySnip); } pcMembers.Add(s); }, Platform.Windows); dom.AddReadonlyMembers(this, delegate(CodeTypeMember s, string c) { CodeTypeMember readonlySnip = directives.CreateReadOnlySnippet(); Comment(readonlySnip ?? s, c); if (readonlySnip != null) { xboxMembers.Add(readonlySnip); } xboxMembers.Add(s); }, Platform.Xbox); } } if (pcMembers.Count > 0 || xboxMembers.Count > 0) { //add #if / else blocks classDom.Members.Add(directives.IfXboxStatement); foreach (CodeTypeMember type in xboxMembers) { classDom.Members.Add(type); } classDom.Members.Add(directives.ElseStatement); foreach (CodeTypeMember type in pcMembers) { classDom.Members.Add(type); } classDom.Members.Add(directives.EndifStatement); } //finally, create the attribute setters CreateSetAttributeMethod(typeof(float), "SetAttribute", "attribute"); CreateSetAttributeMethod(typeof(Vector2), "SetAttribute", "attribute"); CreateSetAttributeMethod(typeof(Vector3), "SetAttribute", "attribute"); CreateSetAttributeMethod(typeof(Vector4), "SetAttribute", "attribute"); CreateSetAttributeMethod(typeof(Matrix), "SetAttribute", "attribute"); CreateSetAttributeMethod(typeof(bool), "SetAttribute", "attribute"); CreateSetAttributeMethod(typeof(float[]), "SetAttribute", "attribute"); CreateSetAttributeMethod(typeof(Vector2[]), "SetAttribute", "attribute"); CreateSetAttributeMethod(typeof(Vector3[]), "SetAttribute", "attribute"); CreateSetAttributeMethod(typeof(Vector4[]), "SetAttribute", "attribute"); CreateSetAttributeMethod(typeof(Matrix[]), "SetAttribute", "attribute"); CreateSetAttributeMethod(typeof(Xen.Graphics.State.TextureSamplerState), "SetSamplerState", "sampler"); CreateSetAttributeMethod(typeof(Texture), "SetTexture", "texture"); CreateSetAttributeMethod(typeof(Texture2D), "SetTexture", "texture"); CreateSetAttributeMethod(typeof(Texture3D), "SetTexture", "texture"); CreateSetAttributeMethod(typeof(TextureCube), "SetTexture", "texture"); }