Skip to content

Commit

Permalink
Add preliminary GLSL support (compiler-explorer#6883)
Browse files Browse the repository at this point in the history
Part of
compiler-explorer#2331
Inspired by
compiler-explorer#3932

I think it is great that HLSL has support here, but the lack of GLSL
support is what stops me from using Compiler-Explorer more often. LunarG
also have shown in our [yearly ecosystem
survey](https://www.lunarg.com/wp-content/uploads/2024/04/2024-Vulkan-Ecosystem-Survey-Results-04-04-2024.pdf)
that GLSL is very widely used in the GPU space

![image](https://github.com/user-attachments/assets/ec740d61-0bf4-42b2-8e51-c204819aba11)

A while ago I started to create [my own SPIR-V
tool](https://github.com/sjfricke/SPIRV-Playground) but was given
feedback to "please just spend your free-time efforts making
compiler-explorer better for SPIR-V instead" ... to which I agree (since
seems a LOT of ground work was already laid out for me 😄 )

So here it is, a working version of GLSL using `glslang` 🚀 


![image](https://github.com/user-attachments/assets/2fc67890-1cd2-4b7e-82c2-30ca135f8590)

I guess beside reviewing my very unused Typescript skills, I know we
will need to add things to the Infra repo to get things public. For that
I am not sure what the best course of action is, we do have [rolling
releases](https://github.com/KhronosGroup/glslang/releases/tag/main-tot)
of `glslang` as well as SDK version tags

---------

Co-authored-by: Matt Godbolt <[email protected]>
  • Loading branch information
spencer-lunarg and mattgodbolt authored Oct 1, 2024
1 parent 49aa860 commit 6924100
Show file tree
Hide file tree
Showing 9 changed files with 882 additions and 0 deletions.
7 changes: 7 additions & 0 deletions .github/labeler.yml
Original file line number Diff line number Diff line change
Expand Up @@ -180,6 +180,13 @@
- 'etc/config/jakt.*.properties'
- 'static/modes/jakt-mode.ts'

'lang-glsl':
- changed-files:
- any-glob-to-any-file:
- 'lib/compilers/glsl.ts'
- 'etc/config/glsl.*.properties'
- 'static/modes/glsl-mode.ts'

'lang-go':
- changed-files:
- any-glob-to-any-file:
Expand Down
12 changes: 12 additions & 0 deletions etc/config/glsl.defaults.properties
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
compilers=&glslang

defaultCompiler=glslangValidator
supportsBinary=false
compilerType=glsl
instructionSet=spirv

disassemblerPath=/opt/compiler-explorer/SPIRV-Tools-master/build/tools/spirv-dis

group.glslang.compilers=glslangValidator
compiler.glslangValidator.exe=/usr/bin/glslangValidator
compiler.glslangValidator.name=glslang
12 changes: 12 additions & 0 deletions examples/glsl/default.glsl
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
// This will be consumed as a .glsl file and needs the stage and target profile. Example options:
// -S comp --target-env vulkan1.1
#version 450
layout(set = 0, binding = 0, rgba8) readonly uniform image2D myImage;
layout(set = 0, binding = 1, std430) buffer SSBO {
ivec2 coords;
vec4 data;
};

void main() {
data = imageLoad(myImage, coords);
}
1 change: 1 addition & 0 deletions lib/compilers/_all.ts
Original file line number Diff line number Diff line change
Expand Up @@ -77,6 +77,7 @@ export {GCCCompiler} from './gcc.js';
export {GCCRSCompiler} from './gccrs.js';
export {GCCGimpleCompiler} from './gimple.js';
export {GCCCobolCompiler} from './gcccobol.js';
export {GLSLCompiler} from './glsl.js';
export {GnuCobolCompiler} from './gnucobol.js';
export {GolangCompiler} from './golang.js';
export {HaskellCompiler} from './haskell.js';
Expand Down
98 changes: 98 additions & 0 deletions lib/compilers/glsl.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,98 @@
// Copyright (c) 2024, Compiler Explorer Authors
// All rights reserved.
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are met:
//
// * Redistributions of source code must retain the above copyright notice,
// this list of conditions and the following disclaimer.
// * Redistributions in binary form must reproduce the above copyright
// notice, this list of conditions and the following disclaimer in the
// documentation and/or other materials provided with the distribution.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
// AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
// IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
// ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
// LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
// CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
// SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
// INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
// CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
// ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
// POSSIBILITY OF SUCH DAMAGE.

import path from 'path';

import type {ExecutionOptions} from '../../types/compilation/compilation.interfaces.js';
import type {ParseFiltersAndOutputOptions} from '../../types/features/filters.interfaces.js';
import {BaseCompiler} from '../base-compiler.js';
import {logger} from '../logger.js';
import {SPIRVAsmParser} from '../parsers/asm-parser-spirv.js';
import * as utils from '../utils.js';

export class GLSLCompiler extends BaseCompiler {
protected disassemblerPath: string;

static get key() {
return 'glsl';
}

constructor(info: any, env: any) {
super(info, env);

this.asm = new SPIRVAsmParser(this.compilerProps);

this.disassemblerPath = this.compilerProps<string>('disassemblerPath');
}

getPrimaryOutputFilename(dirPath: string, outputFilebase: string) {
return path.join(dirPath, `${outputFilebase}.spv`);
}

override optionsForFilter(filters: ParseFiltersAndOutputOptions, outputFilename: string) {
const sourceDir = path.dirname(outputFilename);
const spvBinFilename = this.getPrimaryOutputFilename(sourceDir, this.outputFilebase);
return ['-o', spvBinFilename, '-g']; // -g provides debug info
}

// TODO: Check this to see if it needs key (same in clspv)
override getOutputFilename(dirPath: string, outputFilebase: string) {
return path.join(dirPath, `${outputFilebase}.spvasm`);
}

override async runCompiler(
compiler: string,
options: string[],
inputFilename: string,
execOptions: ExecutionOptions & {env: Record<string, string>},
) {
const sourceDir = path.dirname(inputFilename);
const spvBinFilename = this.getPrimaryOutputFilename(sourceDir, this.outputFilebase);

if (!execOptions) {
execOptions = this.getDefaultExecOptions();
}
execOptions.customCwd = path.dirname(inputFilename);

const spvBin = await this.exec(compiler, options, execOptions);
const result = this.transformToCompilationResult(spvBin, inputFilename);

if (spvBin.code !== 0 || !(await utils.fileExists(spvBinFilename))) {
return result;
}

const spvasmFilename = this.getOutputFilename(sourceDir, this.outputFilebase);
const disassemblerFlags = [spvBinFilename, '-o', spvasmFilename];

const spvasmOutput = await this.exec(this.disassemblerPath, disassemblerFlags, execOptions);
if (spvasmOutput.code !== 0) {
logger.error('SPIR-V binary to text failed', spvasmOutput);
}

result.stdout = result.stdout.concat(utils.parseOutput(spvasmOutput.stdout));
result.stderr = result.stderr.concat(utils.parseOutput(spvasmOutput.stderr));
result.languageId = 'spirv';
return result;
}
}
11 changes: 11 additions & 0 deletions lib/languages.ts
Original file line number Diff line number Diff line change
Expand Up @@ -397,6 +397,17 @@ const definitions: Record<LanguageKey, LanguageDefinition> = {
previewFilter: null,
monacoDisassembly: null,
},
glsl: {
name: 'GLSL',
monaco: 'glsl',
extensions: ['.glsl'],
alias: [],
logoUrl: null,
logoUrlDark: null,
formatter: null,
previewFilter: null,
monacoDisassembly: null,
},
go: {
name: 'Go',
monaco: 'go',
Expand Down
1 change: 1 addition & 0 deletions static/modes/_all.ts
Original file line number Diff line number Diff line change
Expand Up @@ -44,6 +44,7 @@ import './no-highlight-mode';
import './erlang-mode';
import './fortran-mode';
import './gccdump-rtl-gimple-mode';
import './glsl-mode';
import './haskell-mode';
import './hlsl-mode';
import './hook-mode';
Expand Down
Loading

0 comments on commit 6924100

Please sign in to comment.