Commit Graph

278 Commits

Author SHA1 Message Date
Pierre Moreau
12447d8465 Support OpenCL 1.2 and 2.0 target environments
include: Add target environment enums for OpenCL 1.2 and 2.0

Validator: Validate OpenCL capabilities

Update validate capabilities to handle embedded profiles

Add test for OpenCL capabilities validation

Update messages to mention the OpenCL profile used

Re-format val_capability_test.cpp
2017-12-12 11:35:39 -05:00
Alan Baker
867451f49e Add scalar replacement
Adds a scalar replacement pass. The pass considers all function scope
variables of composite type. If there are accesses to individual
elements (and it is legal) the pass replaces the variable with a
variable for each composite element and updates all the uses.

Added the pass to -O
Added NumUses and NumUsers to DefUseManager
Added some helper methods for the inst to block mapping in context
Added some helper methods for specific constant types

No longer generate duplicate pointer types.

* Now searches for an existing pointer of the appropriate type instead
of failing validation
* Fixed spec constant extracts
* Addressed changes for review
* Changed RunSinglePassAndMatch to be able to run validation
 * current users do not enable it

Added handling of acceptable decorations.

* Decorations are also transfered where appropriate

Refactored extension checking into FeatureManager

* Context now owns a feature manager
 * consciously NOT an analysis
 * added some test
* fixed some minor issues related to decorates
* added some decorate related tests for scalar replacement
2017-12-11 10:51:13 -05:00
Steven Perron
5d602abd66 Add global redundancy elimination
Adds a pass that looks for redundant instruction in a function, and
removes them.  The algorithm is a hash table based value numbering
algorithm that traverses the dominator tree.

This pass removes completely redundant instructions, not partially
redundant ones.
2017-12-07 18:35:38 -05:00
Lei Zhang
aec60b8158 Add RegisterLegalizationPasses() into the interface
Add note to mention the use scenario.  The original list came
from Glslang.
2017-11-23 17:26:44 -05:00
Steven Perron
28c415500d Create a local value numbering pass
Creates a pass that removes redundant instructions within the same basic
block.  This will be implemented using a hash based value numbering
algorithm.

Added a number of functions that check for the Vulkan descriptor types.
These are used to determine if we are variables are read-only or not.

Implemented a function to check if loads and variables are read-only.
Implemented kernel specific and shader specific versions.

A big change is that the Combinator analysis in ADCE is factored out
into the IRContext as an analysis. This was done because it is being
reused in the value number table.
2017-11-23 11:45:09 -05:00
Alan Baker
a771713e42 Adding an unique id to Instruction generated by IRContext
Each instruction is given an unique id that can be used for ordering
purposes. The ids are generated via the IRContext.

Major changes:
* Instructions now contain a uint32_t for unique id and a cached context
pointer
 * Most constructors have been modified to take a context as input
 * unfortunately I cannot remove the default and copy constructors, but
 developers should avoid these
* Added accessors to parents of basic block and function
* Removed the copy constructors for BasicBlock and Function and replaced
them with Clone functions
* Reworked BuildModule to return an IRContext owning the built module
 * Since all instructions require a context, the context now becomes the
basic unit for IR
* Added a constructor to context to create an owned module internally
* Replaced uses of Instruction's copy constructor with Clone whereever I
found them
* Reworked the linker functionality to perform clones into a different
context instead of moves
* Updated many tests to be consistent with the above changes
 * Still need to add new tests to cover added functionality
* Added comparison operators to Instruction
* Added an internal option to LinkerOptions to verify merged ids are
unique
* Added a test for the linker to verify merged ids are unique

* Updated MergeReturnPass to supply a context
* Updated DecorationManager to supply a context for cloned decorations

* Reworked several portions of the def use tests in anticipation of next
set of changes
2017-11-20 17:49:10 -05:00
Alan Baker
a92d69b43d Initial implementation of merge return pass.
Works with current DefUseManager infrastructure.

Added merge return to the standard opts.

Added validation to passes.

Disabled pass for shader capabilty.
2017-11-15 10:27:04 -05:00
Steven Perron
716138ee14 Add option to relax validation of store types.
There are a number of users of spriv-opt that are hitting errors
because of stores with different types.  In general, this is wrong, but,
in these cases, the types are the exact same except for decorations.

The options is "--relax-store-struct", and it can be used with the
validator or the optimizer.

We assume that if layout information is missing it is consistent.  For
example if one struct has a offset of one of its members, and the other
one does not, we will still consider them as being layout compatible.
The problem will be if both struct has and offset decoration for
corresponding members, and the offset are different.
2017-10-28 18:48:21 -04:00
Steven Perron
5834719fc1 Add pass to remove dead variables at the module level.
There does not seem to be any pass that remove global variables.  I
think we could use one.  This pass will look specifically for global
variables that are not referenced and are not exported.  Any decoration
associated with the variable will also be removed.  However, this could
cause types or constants to become unreferenced.  They will not be
removed.  Another pass will have to be called to remove those.
2017-10-23 13:57:05 -04:00
Diego Novillo
c75704ec08 CFG cleanup pass - Remove unreachable blocks.
- Adds a new pass CFGCleanupPass.  This serves as an umbrella pass to
  remove unnecessary cruft from a CFG.
- Currently, the only cleanup operation done is the removal of
  unreachable basic blocks.
- Adds unit tests.
- Adds a flag to spirvopt to execute the pass (--cfg-cleanup).
2017-10-19 15:16:29 -04:00
Andrey Tuganov
2401fc0a72 Refactored MARK-V API
- switched from C to C++
- moved MARK-V model creation from backend to frontend
- The same MARK-V model object can be used to encode/decode multiple
files
- Added MARK-V model factory (currently only one option)
- Added --validate option to spirv-markv (run validation while
encoding/decoding)
2017-10-12 15:40:40 -04:00
Diego Novillo
c90d7305e7 Add -O, -Os and -Oconfig flags.
These flags are expanded to a series of spirv-opt flags with the
following semantics:

-O: expands to passes that attempt to improve the performance of the
    generated code.

-Os: expands to passes that attempt to reduce the size of the generated
     code.

-Oconfig=<file> expands to the sequence of passes determined by the
                flags specified in the user-provided file.
2017-10-10 12:14:09 -04:00
Pierre Moreau
86627f7b3f Implement Linker (module combiner)
Add extra iterators for ir::Module's sections
Add extra getters to ir::Function
Add a const version of BasicBlock::GetLabelInst()

Use the max of all inputs' version as version

Split debug in debug1 and debug2
- Debug1 instructions have to be placed before debug2 instructions.

Error out if different addressing or memory models are found

Exit early if no binaries were given

Error out if entry points are redeclared

Implement copy ctors for Function and BasicBlock
- Visual Studio ends up generating copy constructors that call deleted
  functions while compiling the linker code, while GCC and clang do not.
  So explicitly write those functions to avoid Visual Studio messing up.

Move removing duplicate capabilities to its own pass

Add functions running on all IDs present in an instruction

Remove duplicate SpvOpExtInstImport

Give default options value for link functions

Remove linkage capability if not making a library

Check types before allowing to link

Detect if two types/variables/functions have different decorations

Remove decorations of imported variables/functions and their types

Add a DecorationManager

Add a method for removing all decorations of id

Add methods for removing operands from instructions

Error out if one of the modules has a non-zero schema

Update README.md to talk about the linker

Do not freak out if an imported built-in variable has no export
2017-10-06 18:33:53 -04:00
Andrey Tuganov
4b1577a0cb Remove duplicate dead branch elim pass declaration
The function had two declarations in the same header with somewhat
different comments.
2017-10-06 17:05:46 -04:00
Lei Zhang
99cd25c413 Remove duplicated declaration of CreateAggressiveDCEPass(). 2017-09-26 15:39:00 -04:00
Steven Perron
e43c91046b Create the dead function elimination pass
Creates a pass called eliminate dead functions that looks for functions
that could never be called, and deletes them from the module.

To support this change a new function was added to the Pass class to
traverse the call trees from diffent starting points.

Includes a test to ensure that annotations are removed when deleting a
dead function.  They were not, so fixed that up as well.

Did some cleanup of the assembly for the test in pass_test.cpp.  Trying
to make them smaller and easier to read.
2017-09-26 11:18:06 -04:00
Steven Perron
e4c7d8e748 Add strength reduction; for now replace multiply by power of 2
Create a new optimization pass, strength reduction, which will replace
integer multiplication by a constant power of 2 with an equivalent bit
shift.  More changes could be added later.

- Does not duplicate constants

- Adds vector |Concat| utility function to a common test header.
2017-09-18 17:01:36 -04:00
GregF
429ca05b3f Opt: Create InlineOpaquePass
Only inline calls to functions with opaque params or return

TODO: Handle parameter type or return type where the opqaue
type is buried within an array.
2017-08-18 18:04:30 -04:00
GregF
b0310a4156 ADCE: Add support for function calls
ADCE will now generate correct code in the presence of function calls.
This is needed for opaque type optimization needed by glslang. Currently
all function calls are marked as live. TODO: mark calls live only if they
write a non-local.
2017-08-10 17:30:05 -04:00
GregF
e28bd39997 Inline: Split out InlineExhaustivePass from InlinePass 2017-08-04 17:56:46 -04:00
GregF
f4b29f3bf7 Add CommonUniformElim pass
- UniformElim: Only process reachable blocks

- UniformElim: Don't reuse loads of samplers and images across blocks.
  Added a second phase which only reuses loads within a block for samplers
  and images.

- UniformElim: Upgrade CopyObject skipping in GetPtr

- UniformElim: Add extensions whitelist
  Currently disallowing SPV_KHR_variable_pointers because it doesn't
  handle extended pointer forms.

- UniformElim: Do not process shaders with GroupDecorate

- UniformElim: Bail on shaders with non-32-bit ints.

- UniformElim: Document support for only single index and add TODO.
2017-08-03 11:34:58 -04:00
GregF
9de4e69856 Add AggressiveDCEPass
Create aggressive dead code elimination pass
This pass eliminates unused code from functions. In addition,
it detects and eliminates code which may have spurious uses but which do
not contribute to the output of the function. The most common cause of
such code sequences is summations in loops whose result is no longer used
due to dead code elimination. This optimization has additional compile
time cost over standard dead code elimination.

This pass only processes entry point functions. It also only processes
shaders with logical addressing. It currently will not process functions
with function calls. It currently only supports the GLSL.std.450 extended
instruction set. It currently does not support any extensions.

This pass will be made more effective by first running passes that remove
dead control flow and inlines function calls.

This pass can be especially useful after running Local Access Chain
Conversion, which tends to cause cycles of dead code to be left after
Store/Load elimination passes are completed. These cycles cannot be
eliminated with standard dead code elimination.

Additionally: This transform uses a whitelist of instructions that it
knows do have side effects, (a.k.a. combinators).  It assumes other
instructions have side effects: it will not remove them, and assumes
they have side effects via their ID operands.
2017-07-10 11:30:25 -04:00
GregF
cc8bad3a5b Add LocalMultiStoreElim pass
A SSA local variable load/store elimination pass.
For every entry point function, eliminate all loads and stores of function
scope variables only referenced with non-access-chain loads and stores.
Eliminate the variables as well.

The presence of access chain references and function calls can inhibit
the above optimization.

Only shader modules with logical addressing are currently processed.
Currently modules with any extensions enabled are not processed. This
is left for future work.

This pass is most effective if preceeded by Inlining and
LocalAccessChainConvert. LocalSingleStoreElim and LocalSingleBlockElim
will reduce the work that this pass has to do.
2017-07-07 17:54:21 -04:00
GregF
52e247f221 DeadBranchElim: Add DeadBranchElimPass 2017-07-07 15:16:25 -04:00
Andrey Tuganov
73e8dac5b9 Added compression tool tools/spirv-markv. Work in progress.
Command line application is located at tools/spirv-markv
API at include/spirv-tools/markv.h

At the moment only very basic compression is implemented, mostly varint.
Scope of supported SPIR-V opcodes is also limited.

Using a simple move-to-front implementation instead of encoding mapped
ids.

Work in progress:
- Does not cover all of SPIR-V
- Does not promise compatibility of compression/decompression across
  different versions of the code.
2017-06-30 12:22:48 -04:00
GregF
ad1d0351a0 BlockMerge: Add BlockMergePass
Also, add BasicBlock::tail()
2017-06-27 11:31:33 -04:00
Rex Xu
5fbbadca4e Add support for SPV AMD extensions 2017-06-21 15:08:07 -04:00
GregF
6136bf9e0b mem2reg: Add InsertExtractElimPass 2017-06-21 08:13:15 -04:00
GregF
0c5722fc01 mem2reg: Add LocalSingleStoreElimPass
Eliminate function scope variables with one store, if possible.
2017-06-19 10:43:02 -04:00
GregF
7c8da66bc2 mem2reg: Add pass to eliminate local loads and stores in single block. 2017-06-12 17:03:47 -04:00
GregF
aa7e687ef0 Mem2Reg: Add Local Access Chain Convert pass
- Supports OpAccessChain and OpInBoundsAccessChain
- Does not process modules with non-32-bit integer types.
2017-06-04 12:49:27 -04:00
David Neto
dbc2049aa3 Add SPIR-V 1.2 support, for OpenCL 2.2 2017-05-15 17:10:07 -04:00
qining
144f59e451 Add bit pattern interface for setting default value for spec constants 2017-04-21 11:22:47 -04:00
Andrey Tuganov
1e309af80a Added --compact-ids to /tools/opt
The pass remaps ids to a compact set which starts with %1 and
has no gaps.
2017-04-20 10:54:39 -04:00
Andrey Tuganov
b173d1c3cd Added option --preserve-numeric-ids to tools/spirv-as
Added options to tools::Assemble
2017-04-13 14:13:33 -04:00
David Neto
11a867f412 Add FlattenDecoration transform
Add --flatten-decorations to spirv-opt

Flattens decoration groups.  That is, replace OpDecorationGroup
and its uses in OpGroupDecorate and OpGroupMemberDecorate with
ordinary OpDecorate and OpMemberDecorate instructions.

Fixes https://github.com/KhronosGroup/SPIRV-Tools/issues/602
2017-04-06 11:19:56 -04:00
Greg Fischer
04fcc66743 Add exhaustive function call inlining to spirv-opt
Inlining is done for all functions designated as entry points.

Add optional validation to test fixture method SinglePassRunAndCheck.
2017-03-29 18:02:40 -04:00
David Neto
7fe8a57a5b Support SPV_AMD_gcn_shader
Supported in assembler, disassembler, and binary parser.

The validator does not check SPV_AMD_gcn_shader validation rules
beyond parsing the extension.

Adds generic support for generating instruction tables for vendor
extensions.

Adds generic support for extensions the validator should recognize
(but not check) but which aren't derived from the SPIR-V core
grammar file.

Fixes https://github.com/KhronosGroup/SPIRV-Tools/issues/594
2017-03-23 16:32:35 -04:00
David Neto
c3caa546a0 spirv-val prints warnings
Warnings and info messages go to stdout.
Errors still go to stderr.

Fixes https://github.com/KhronosGroup/SPIRV-Tools/issues/568
2017-03-17 12:48:51 -04:00
David Neto
0066a363d6 Add SpirvTools::Validate that takes an options object
Add spvtools::ValidatorOptions RAII wrapper around
a spv_validator_options value.
2017-03-17 12:48:51 -04:00
Andrey Tuganov
b011633171 Validator checks if operands require extension
If required extension is not found, returning new error
SPV_ERROR_MISSING_EXTENSION.
2017-03-14 13:39:43 -04:00
Ehsan Nasiri
da4ae05638 Add command line options struct for the validator
The limit for the number of struct members is parameterized using
command line options.

Add --max-struct-depth command line option.
Add --max-switch-branches command line option.
Add --max-function-args command line option.
Add --max-control-flow-nesting-depth option.
Add --max-access-chain-indexes option.
2017-02-28 12:00:06 -05:00
Ehsan Nasiri
6c899a52f9 Adding validation for vector data rule.
Number of components in a vector can be 2 or 3 or 4. If Vector16
capability is used, 8 and 16 components are also allowed.
Also added unit tests for vector data rule.
2016-11-08 17:48:30 -05:00
Lei Zhang
5edf054926 Add more Assemble(), Disassemble() and Validate() overloads. 2016-09-21 14:42:04 -04:00
Lei Zhang
620f05e679 Publish the C++ interface. 2016-09-21 14:41:47 -04:00
Umar Arshad
bf467da9c9 Update validate interface to accept binary pointers 2016-09-19 16:43:28 -04:00
Lei Zhang
755f97f534 Add a callback mechanism for communicating messages to callers.
Every time an event happens in the library that the user should be
aware of, the callback will be invoked.

The existing diagnostic mechanism is hijacked internally by a
callback that creates an diagnostic object each time an event
happens.
2016-09-15 12:35:48 -04:00
David Neto
4e2ed04d6e Clarify: Ok to pass null diagnostic to spvBinaryParse
It's a valid use case: I might mostly trust my binaries and I don't
care to to collect detailed diagnostic feedback.
2016-09-14 15:19:10 -04:00
David Neto
9fc8658ef3 Relicense SPIRV-Tools under Apache 2.0
Fixes https://github.com/KhronosGroup/SPIRV-Tools/issues/383

Finalize v2016.4
2016-09-02 10:00:29 -04:00
David Neto
c296701964 Add target envs for OpenCL, OpenGL
Covers: OpenCL 2.1, OpenCL 2.2
Covers: OpenGL 4.0, OpenGL 4.1, OpenGL 4.2, OpenGL 4.3, OpenGL 4.5.
The OpenGL environments assume the use of GL_ARB_gl_spirv, of course.
2016-08-05 18:19:30 -04:00
David Neto
0bdcc23f7e Disassembling: map IDs to friendly names.
Add a FriendlyNameMapper to deduce friendly names for IDs based on
OpName, type structure, etc.
2016-07-19 16:28:17 -04:00
Lei Zhang
200e897887 Add an option to spvBinaryToText() to ignore header output. 2016-06-27 15:25:24 -04:00
Lei Zhang
10dba91781 Use SPIR-V headers from the KhronosGroup/SPIRV-Headers repo. 2016-06-10 08:48:37 -04:00
Dejan Mircevski
faad7fea3d Test ABGR image channel order.
Update include/spirv/spirv.h from SPIRV-Headers.
2016-05-11 15:14:21 -04:00
David Neto
9166854ac9 Add CHANGES file with high level software history
Add a high level version number for SPIRV-Tools, beginning
with v2016.0-dev.  The README describes the format of the
version number.

The high level version number is extracted from the CHANGES
file.  That works around:
 - stale-bait for when we don't add tags to the repository
 - our inability to add tags to the repository

Option --version causes spirv-as, spirv-dis, and spirv-val to
show the high level version number.

Add spvSoftwareVersionString to return the C-string for
the high level version number.

Add spvSoftwareVersionDetailsString() so that clients can get
more information if they want to.
Also allows us to clean up the uses in the tool executables files,
so now only one file includes build-version.inc.

Move the update-build-version logic to the only
CMakeLists file that needs it.

The update build version script takes a new argument
to name the output file.
2016-04-22 15:19:45 -04:00
Dejan Mircevski
7b33485f6e First tests for SPIR-V v1.1.
Add test for named-barrier instructions and capability.

Add spv_target_env as an optional argument to CompileSuccessfully() and
CompileFailure().  Currently defaults to UNIVERSAL_1_0, though that
could change in the future.

Make spv_context a local variable in test methods instead of a
TextToBinaryTestBase member.  Introduce ScopedContext to make temp
contexts easier.
2016-04-19 16:34:12 -04:00
Dejan Mircevski
cb3c49ef82 Add SPIR-V 1.1 grammar.
Switch to SPIR-V 1.1 as default.
Introduce SPV_ENV_UNIVERSAL_1_1.
Add "1_0" to the internal variable names.
Add spv_target_env to spv*GetTable().
2016-04-18 10:45:57 -04:00
Dejan Mircevski
8ba7c92a94 Remove revision from SPV_ENV_*.
Revisions proliferate quickly and we don't promise to retain extra
grammar copies for every historical one.
2016-04-11 15:31:00 -04:00
Dejan Mircevski
3fb2676d23 Fix validation of array length. 2016-04-04 15:55:05 -04:00
Lei Zhang
6fa3f8aad9 Remove dependency on SPIR-V headers in libspirv.h.
For fulfilling this purpose, the |opcode| field in the
|spv_parsed_instruction_t| struct is changed to of type uint16_t.

Also add functions to query the information of a given SPIR-V
target environment.
2016-04-04 10:34:28 -04:00
Dejan Mircevski
3d27da4bc7 Add a target environment to spvContextCreate().
Run clang-format.
2016-03-31 12:16:51 -04:00
David Neto
6836e17f24 OpExecutionMode only takes a single ExecutionMode
Previously, the grammar allowed many execution modes for a single
OpExecutionMode instruction.

Removes the variable- and optional- execution mode operand type
enum values.

Issue found by antiagainst@
2016-03-29 14:51:02 -04:00
Andrew Woloszyn
4c657bfa8f Make everything compile cleanly with -Wpedantic.
This makes SPIRV_WARN_EVERYTHING compile cleanly.
2016-03-21 10:01:13 -04:00
Dejan Mircevski
c31a31942b Make libspirv.h more C friendly.
In C, `#include <stdbool.h>` so `bool` is recognized.

Add a `typedef` for `spv_context_t`.
2016-03-01 12:38:59 -05:00
Lei Zhang
b6ccd0d891 Remove spv_validate_options_t and change tests accrodingly.
Users always want to run all the checks. The spv_validate_options_t
mechanism, which provides little benefits to users, complicates the
internal implementation and also makes the tests exercise different
paths as users do.

Right now the tests are more like integration tests instead of
unit tests, which should be our next refactoring aim.
2016-02-23 16:19:33 -05:00
David Neto
4d2f2239bf SPIR-V Tools fully supports SPIR-V 1.0 Rev3
- Update version numbers in libspirv.h.
  Add a test for the relevant macros.
- Update the README
2016-02-17 16:01:39 -05:00
David Neto
5a70335bf1 Rearrange headers
Now we have public headers arranged as follows:
$SPIRV_TOOLS_ROOT/include/spirv-tools/libspirv.h
$SPIRV_TOOLS_ROOT/include/spirv/spirv.h
$SPIRV_TOOLS_ROOT/include/spirv/GLSL.std.450.h
$SPIRV_TOOLS_ROOT/include/spirv/OpenCL.std.h

A project should use -I$SPIRV_TOOLS_ROOT/include
and then #include "spirv-tools/libspirv.h"

The headers from the SPIR-V Registry can be accessed as "spirv/spirv."
for example.

The install target should also install the headers from the SPIR-V
Registry.  The libspirv.h header is broken otherwise.

The SPIRV-Tools library depends on the headers from the SPIR-V Registry.

The util/bitutils.h and util/hex_float.h are pulled into the internal
source tree.  Those are not part of the public API to SPIRV-Tools.
2016-02-17 14:49:44 -05:00
David Neto
2889a0c21c Use syntax tables for SPIR-V 1.0 Rev3
- The SPIR-V spec generator has changed how it represents optional
  operands.  Now it tracks a separate boolean flag indicating optionality.
  However, SPIRV-Tools still wants to represent both operand class
  and optionality in the same enums space (SPV_OPERAND_TYPE_*).
  So there's extra work in the patch.

- In the spec generator, OperandImage is now OperandImageOperands.
  This affects enum translation in opcode.cpp.

- In the spec generator, image operands are explicitly followed by
  Id, and VariableIds.  However, SPIRV-Tools uses the bits set
  in the image operand bitmask to control the number and meaning
  of the Ids that follow.  So in writing the opcode.inc syntax
  table, drop all operands after OperandImageOperands.

- Some enums are now more explicitly represented in the generated
  opcode.inc:
    - AccessQualifier (e.g. on OpTypeImage), in both required and
      optional flavours.
    - MemoryAccess (e.g. on loads and stores)

- Add SPV_OPERAND_TYPE_OPTIONAL_ACCESS_QUALIFIER

- Add tests for the optional AccessQualifier operand on OpTypeImage.

- Update the AccessQualifier test for OpTypeImage so it's a round
  trip test through the disassembler as well.
2016-02-16 16:47:04 -05:00
David Neto
0c0a07f0aa Don't promise particular values when float parsing fails.
This should address problems on Windows:
https://github.com/KhronosGroup/SPIRV-Tools/issues/104
2016-02-16 12:13:51 -05:00
David Neto
c7a9a909a8 Parse overflow for fp16 like for 32- and 64-bit
In that case, set the stream fail bit, and set the maximum normal
value or lowest normal value, depending on the sign of the original
value.
2016-02-15 09:31:10 -05:00
David Neto
6bad02c320 Float literal parsing fixes
- For 32- and 64-bit floats, overflow is a parse error

  This works around a difference between Xcode's istringstream
  and other platforms.  Xcode's runtime library will happlily
  "round up" overflow values to infinity.  We want to make it fail.

- When parsing a float fails due to bad syntax, follow C++11
  behaviour for operator>> and set the value to zero.

- When parsing a 32-bit or 64-bit float overflows, follow C++11
  behaviour for operator>> and set the value to the nearest
  normal value: either max or lowest finite value for the type.

- Add FloatProxy<T>::max() and ::lowest()

- Make 16-bit overflow behaviour more consistent: we always get a
  16-bit infinity of the right sign, whether the original string
  is a normal value for 32-bit or an overflow value for 32-bit.
  That matches our earlier intent.
  Added TODO's to make 16-bit overflow always an error, just like
  for 32-bit and 64-bit.

- Simplify normal parsing of Float16 values by delegating to
  normal parsing of 32-bit floats.
2016-02-12 16:01:42 -05:00
David Neto
000cad9cc6 Reject float literals with two leading signs
E.g. --1 should be rejected.
2016-02-11 14:11:16 -05:00
David Neto
b5267569d1 Add spvOperandIsConcreteMask 2016-02-02 12:05:34 -05:00
Dejan Mircevski
0c8bdfe163 Use AssemblyGrammar for capability validation.
Also:
- ForEach() for spv_capability_mask_t.
- Add capability min/max constants.
- Move max definition from validate_types.cpp to spirv_definition.h.
2016-02-02 11:40:05 -05:00
Umar Arshad
61a627586b Initial capability implementation and unit tests
* Register capabilility and checks
* Add validate storage class capabilities checks and tests
* Instruction pass refactor
  - More generic form of capability checking by checking operands
    instead of instructions
* Execution Model capabilities checks
* Decorate BuiltIn capability checks
* Addressing Model capability checks
* Memory Model capability checks
* Execution Mode capability checks
* Dim capability checks
* SamplerAddressingMode capability checks
2016-01-27 08:37:23 -05:00
David Neto
c62f41e281 Add disassembler option to show byte offset
The option is disabled by default.

The offset is printed in hex, as a comment after each instruction.
2016-01-20 17:07:30 -05:00
Umar Arshad
1ddeb246eb Validation refactor
* Organize passes into seperate files
* Remove module layout logic from Cfg pass
* Remove module layout logic from Functions class
* Refactor ModuleLayoutPass for readability
* Adapt consistent naming of layout sections (Stage/Section -> Section)
2016-01-14 21:59:28 -05:00
Norbert Nopper
32197bdcd7 Fix, that spirv-tools did not build, as two casts are not present. 2016-01-13 10:29:18 -05:00
Andrew Woloszyn
7ffd8ffeb2 Minor fixes to remove warnings in VS2013.
Also fixes VS2015 build due to missing #include <iterator>
2016-01-11 16:22:34 -05:00
David Neto
5d30edb36d spvDiagnosticDestroy is safe to call on nullptr
Fixes https://github.com/KhronosGroup/SPIRV-Tools/issues/62
2016-01-11 14:26:46 -05:00
Andrew Woloszyn
7a35473573 Made compilation with gcc and clang more strict.
Added additional compilation flags to gcc and clang builds.
Adds -Wall -Wextra -Wno-long-long -Wshadow -Wundef -Wconversion
-WNo-sign-conversion and -Wno-missing-field-initializers
where appropriate.

Does not add -Wundef to tests, because GTEST tests undefined
macros all over the place.
2016-01-11 10:54:20 -05:00
Andrew Woloszyn
43401d2ed0 Support 16-bit float in assembler and disassembler
This adds half-precision constants to spirv-tools.
16-bit floats are always disassembled into hex-float format,
but can be assembled from floating point or hex-float inputs.
2016-01-08 10:48:39 -05:00
Dejan Mircevski
b6fe02fc39 Extend copyright to 2016. 2016-01-07 13:44:22 -05:00
David Neto
ae7d707fdb Fix shadowing warnings reported by GCC 2016-01-06 17:36:33 -05:00
David Neto
ba73a7cee5 Fix conversion warnings reported by GCC. 2016-01-06 17:36:33 -05:00
David Neto
f80b51fa9b Fix var shadowing and width mismatches in hex_float.h 2016-01-06 13:11:42 -05:00
David Neto
d0de196439 operator<< on FloatProxy preserves float and fill
Fixes formatting of disassembler output after printing
a hex float, e.g. for a NaN or subnormal.
2016-01-05 12:49:55 -05:00
Umar Arshad
a3d0d3c719 Initial logical layout validation
* Validates module level instructions for logical layout
  conformance
* Does not validate:
  1. Function logical layout
  2. Minor cases with OpVariable
  3. Missing MemoryModel instruction in module
  4. Order of function definition and function declaration
* 782 unit tests for logical layout

Addressed feedback
2015-12-17 15:58:09 -05:00
Umar Arshad
6d37e3c5f3 Refactor validation types into another file 2015-12-17 15:56:58 -05:00
Umar Arshad
b9ad418c95 Fix warnings with Apple clang++
* Unused private member
* Overflow error when subtracting num_fraction_bits for HF16 and HF
2015-12-10 13:15:06 -05:00
Umar Arshad
f76e0f5231 Basic SSA Validation
Most uses of an ID must occur after the definition
of the ID.  Forward references are allowed for
things like OpName, OpDecorate, and various cases
of control-flow instructions such as OpBranch, OpPhi,
and OpFunctionCall.

TODO: Use CFG analysis for SSA checks.  In particular,
an ID defined inside a function body is only usable inside
that function body.  Also, use dominator info to catch
some failing cases.

Also:
* Validator test cases use (standard) assignment form.
* Update style to more closely follow the Google C++ style guide
* Remove color-diagnostics flag.
  This is enabled by default on terminals with color. Prints
  hidden ASCII for terminals that can't handle color(Emacs)
* Pass functors to SSAPass to check if the
  operand can be forward referenced based on its index value
* Return SPV_ERROR_INVALID_ID for ID related errors
  spvBinaryParse returned SPV_ERROR_INVALID_BINARY for all types of
  errors. Since spvBinaryParse does some ID validation, this was
  returning inappropriate error codes for some tests.
* Common fixture for validation tests.
  It only runs certian validation passes.
* Add a SPV_VALIDATE_SSA_BIT for testing purposes
* Fixtures now return error codes
* Add OpName support in diag message and unit tests
* Binary parsing can fail with invalid ID or invalid binary error code

Tests include:
* OpDecorate
* OpName
* OpMemberName
* OpBranchConditional
* OpSelectionMerge
* OpMemberDecorate
* OpGroupDecorate
* OpDeviceEnqueue
* Enable several tests failing in ID validation.
2015-12-09 16:15:00 -05:00
Andrew Woloszyn
4e5bc928c0 Added Float16, and HexFloat conversions 2015-12-08 14:41:57 -05:00
David Neto
d9ad050a95 spvBinaryParse: fix overruns, handle image format
Add unit tests for all diagnostics issued by spvBinaryParse.

Handle image format operands in the binary parser and the
disassembler.

Document that the callback function pointers can be null,
in which case they are ignored.

Detect exhaustion of input when parsing an operand,
to avoid buffer overruns on some invalid input cases.

Fix the description strings for some operand types.
Make the diagnostic messages for those operand types
consistent between the assembler and binary parser.

Fixes https://github.com/KhronosGroup/SPIRV-Tools/issues/29
2015-11-30 10:44:23 -05:00
David Neto
ee8a007810 Clarify the non-SPV_SUCCESS case parser callbacks.
When a callback returns something other than SPV_SUCCESS,
then no futher callbacks are issued (parsing terminates early),
and no additional diagnostics are emitted.

The unit tests already check this behaviour.
2015-11-30 10:36:42 -05:00
David Neto
750f205b63 Several unit tests for spvBinaryParse
Add a non-zero spv_result_t value SPV_REQUESTED_TERMINATION
which should be used to signal an ok result, but signals
early termination for a process, such as binary parsing.

Tests include:
 - correct contents sent to header and instruction callbacks
 - non-zero status from a callback should terminate parsing,
   but the parser should not generate its own diagnostic.

TODO: Check diagnostics generated by the parser itself.
2015-11-27 10:19:06 -05:00
David Neto
7bff3eb6f9 spv_parsed_instruction_t cleanup
Add members:
 - words: a pointer to an array of words in the instruction,
   in host native endianness.
 - num_words: sizes the words member

Remove member:
 - offset

This simplifies clients of spvBinaryParse, because they don't
have to handle endianness translation.

Also, it makes the binary parse API more composable, allowing
for easy chaining of binary parse clients.  A binary parse client
is handed the array of words directly instead of having to reference
some external array of all the words in the SPIR-V binary.  It also
allows a binary parse client to mutate the instruction stream before
handing off to a downstream consumer.

TODO(dneto): Still need to write the unit tests for spvBinaryParse

Fixes: https://github.com/KhronosGroup/SPIRV-Tools/issues/1
2015-11-23 09:52:38 -05:00
Ben Vanik
01c8d7a8fb Merge pull request #23.
Fixing some C++ conversion errors.
* Implicit conversion from int to bool.
* Implicit conversion from size_t to uint32_t.
* Implicit conversion from char* to uint8_t.

Adding no-op color operators so unhandled platforms can still link.
2015-11-23 01:42:46 -05:00
Lei Zhang
8bd75d650e Clean up CMake configuration and address compiler warnings.
- Removed dead configuration in CMakeLists.txt.
- Used target_compile_options() instead of CMAKE_{C|CXX}_FLAGS.
- Turned on warnings on tests.
- Fixed various warnings for comparing signed with unsigned values.
- Removed dead code exposed by compiler warnings.
2015-11-18 16:32:41 -05:00
David Neto
64a9be97ca Remove old names for enums: memory semantics, scope ID 2015-11-18 15:56:38 -05:00
David Neto
748d585a9a Object files should depend on spirv.h and friends
Don't use SYSTEM attribute on include_directories directive
for the SPIR-V standard header files.  When you do, object files
are not considered dependent on those headers.

Checked by looking at the dependency file source/disassemble.cpp.o.d,
and by trying to compile after a trivial edit to spirv.h

Fixes https://github.com/KhronosGroup/SPIRV-Tools/issues/7

Also, use "" inclusion instead of <> inclusion for standard SPIR-V
headers.
2015-11-17 18:04:12 -05:00
Lei Zhang
af9906e4e5 Use Google comment style and fix typos. 2015-11-16 17:25:43 -05:00
Lei Zhang
acf7287c42 Fix many typos. 2015-11-13 12:35:43 -06:00
David Neto
3d348a8440 The version header word has 3 byte-size components.
Bits 24-31: 0
Bits 16-23: SPIR-V major number (1)
Bits  8-15: SPIR-V minor number (0)
Bits   0-7: SPIR-V minor number (2)

The assembler will construct the word appropriately,
and the disassemble will print it in major.minor.revision form.
2015-11-13 12:35:34 -06:00
Lei Zhang
972788bf23 Use opaque context object to hold SPIR-V info tables.
Previously the opcode table is declared as an global array and we
have spvOpcodeTableInitialize() modifying it. That can result in
race condition. Now spvOpcodeTabelGet() copies the whole underlying
array.
2015-11-12 16:27:51 -05:00
David Neto
e7c426ac8d Disassembler tool indents to 15 by default
The assigned-to result Id appears to the left of the 15th column.

Add --no-indent option.

The API form of the disassembler does not indent by default.
2015-11-12 16:27:50 -05:00
Lei Zhang
4ac601a2c3 libspirv.h doesn't depend on spirv_operands.hpp anymore.
Also change spirv_operands.hpp to a C header since we only have
an enum inside it, and move it to source/.
2015-11-12 09:43:26 -05:00
Lei Zhang
a23a73671a Moves parser interface to libspirv.h. 2015-11-12 09:43:23 -05:00
Lei Zhang
8984f6f31f Move internal macros/structs for SPIR-V to a separate header. 2015-11-12 09:43:20 -05:00
Lei Zhang
aa056cd8c7 Move SPIR-V constants/limits to a separate header. 2015-11-12 09:43:09 -05:00
Lei Zhang
7a222e4abf Move info table related structs into table.h. 2015-11-12 09:42:58 -05:00
Lei Zhang
04736e7878 Move spv*TableGet() functions out of libspirv.h.
This is a part of the effort to clean up libspirv.h.
2015-11-12 09:42:55 -05:00
Lei Zhang
df920ecb71 Remove table parameters from API functions.
Opcode, operand, and external instruction tables are no longer
passed in as parameters to spvTextToBinary(), spvBinaryToText(),
and spvValidate().
2015-11-12 09:42:50 -05:00
Andrew Woloszyn
ec691fba2a Fixed permissions 2015-11-11 12:12:16 -05:00
Andrew Woloszyn
55ecc2e097 Fixed warnings on windows and constness of spv_binary.
Replaced uint64_t with size_t in the places that make sense and
added spv_const_binary{,_t} to allow the interface to accept non
modifiable spirv where appropriate.
2015-11-11 12:12:13 -05:00
Lei Zhang
9049bb4877 Get magic number and version from spirv.h.
This is a part of the effort to clean up libspirv.h.
2015-11-11 12:12:10 -05:00
David Neto
0f166be68d Assembler support for OpSpecConstantOp
Adds SPV_OPERAND_TYPE_SPEC_CONSTANT_OP_NUMBER.
2015-11-11 12:12:04 -05:00
David Neto
ce9cef71ac Fix Windows build errors.
- uint64_t != size_t sometimes
- don't use C99 runtime sized arrays
2015-11-11 09:55:51 -05:00
David Neto
2ae4a68fe8 Fix handling of OpExtInstImport
The assembler tracks mapping of extended instruction import Id
to extended instruction type.

Adds a few new ways to fail.
2015-11-10 15:58:07 -05:00
David Neto
229b90f6f4 Print OpConstant values according to type.
Zero and normal floating point values are printed with enough
enough digits to reproduce all the bits exactly.
Other float values (subnormal, infinity, and NaN) are printed
as hex floats.

Fix a binary parse bug: Count partially filled words in a
typed literal number operand.

TODO: Assembler support for hex numbers, and therefore reading
infinities and NaNs.
2015-11-10 15:57:59 -05:00
Lei Zhang
9042f40f7c Remove support for canonical assembly syntax format. 2015-11-10 15:57:49 -05:00
David Neto
201caf7001 spv_operand_type_t cleanup.
- Concrete operand types are never optional.
  Split them to make this so, e.g. add SPV_OPERAND_TYPE_IMAGE
  since there was SPV_OPERAND_TYPE_OPTIONAL_IMAGE.
  Similarly for SPV_OPERAND_TYPE_MEMORY_ACCESS.
  This entails duplicating two operand table entries.

- The above, plus some rearranging of enums, allows us to define
  first and last optional operand types, and first and last
  variable operand types.
  This lets us simplify the code for spvOperandIsOptional, and
  spvOperandIsVariable.

- Replace SPV_OPERAND_TYPE_MULTIWORD_LITERAL_NUMBER with the
  more accurately named SPV_OPERAND_TYPE_TYPED_LITERAL_NUMBER.
  Its special characteristic is that the type of the literal
  number is determined by some previous operand in the instruction.
  This is used for literals in OpSwitch, OpConstant, and OpSpecConstant.
  This lets us refactor operand parsing cases in the assembler.

- Remove the special required-thing-in-optional-tuple in favour of
  the corresponding concrete operand type:
        SPV_OPERAND_TYPE_ID_IN_OPTIONAL_TUPLE
    --> SPV_OPERAND_TYPE_ID
        SPV_OPERAND_TYPE_INTEGER_LITERAL_IN_OPTIONAL_TUPLE
    --> SPV_OPERAND_TYPE_INTEGER_LITERAL

- Constrain spvOpeandTypeStr to only have to work for non-variable
  operand types.  Add a test for this.
2015-11-10 15:57:45 -05:00
David Neto
0ca6b59bfd Refactor the binary parser.
The binary parser has a C API, described in binary.h.
Eventually we will make it public in libspirv.h.
The API is event-driven in the sense that a callback is called
when a valid header is parsed, and for each parsed instruction.

Classify some operand types as "concrete".  The binary parser uses
only concrete operand types to describe parsed instructions.

The old disassembler APIs are moved into disassemble.cpp

TODO: Add unit tests for spvBinaryParse.
2015-11-10 15:57:33 -05:00
David Neto
a010444b79 Consts before the type, not after 2015-11-10 15:57:26 -05:00
David Neto
e4945def95 A spv_binary_t points to const code words. 2015-11-10 15:57:22 -05:00
Andrew Woloszyn
b3ae4b9422 Updated comment in SetBits.
It now mentions that it will fail if you try to set a bit that
does not exist.
2015-11-10 15:57:07 -05:00
Andrew Woloszyn
758b347983 Added double tests to HexFloat 2015-11-10 15:57:00 -05:00
Lei Zhang
1a0334edee Run clang-format to enforce Google style globally.
Note that we are more strict than Google style for one aspect:
pointer/reference indicators are adjacent to their types, not
their variables.

find . -name "*.h" -exec clang-format -i {} \;
find . -name "*.cpp" -exec clang-format -i {} \;
2015-11-10 15:56:47 -05:00
Andrew Woloszyn
6dfd4186f5 Updated HexFloat parsing for windows.
It is valid for float values to be modified on copy if they are NaN,
so long as they remain the correct NaN. What this means is that
we can not rely on the float data-type for storing float values
if we want to retain bit patterns.

Added FloatProxy which stores data in an unsigned integer, and updated
the HexFloat template to deal with FloatProxy values instead.
2015-11-02 13:52:31 -05:00
Andrew Woloszyn
0b61c593a2 Added HexFloat reading to HexFloat.
This allows reading of hex-encoded floats.
2015-11-02 13:52:28 -05:00
Andrew Woloszyn
c2887f98bc Added HexFloat helper class to print out floating point numbers.
TODO Add double tests before we actually use this.
2015-11-02 13:52:25 -05:00
Andrew Woloszyn
b78d2d31c5 Changed SetBits to index from LSB and take a size. 2015-11-02 13:52:23 -05:00
Lei Zhang
b36e704a47 Use spirv.h instead of spirv.hpp.
This is a part of the effort to make libspirv.h C-compatible.
2015-11-02 13:52:20 -05:00
David Neto
9f79d789ec Inclusion guards follow Google C++ style
Follow the scheme in
http://google-styleguide.googlecode.com/svn/trunk/cppguide.html#The__define_Guard
except:
 - 'include/' is dropped from the guard token
 - 'source/' is dropped from the guard token
2015-11-02 13:52:15 -05:00
David Neto
1780fc4fcf Update to latest registered generator enums
The registry is at:
https://www.khronos.org/registry/spir-v/api/spir-v.xml
2015-11-02 13:51:54 -05:00
Andrew Woloszyn
f731cbf6c4 Added set_bits<> to bitutils.
This allows us to get a constant with the given bits set at
compile-time. This is needed for a future patch for HexFloat.
2015-11-02 13:51:51 -05:00
Lei Zhang
b998c81315 Use typedef instead of using in libspirv.h.
The header file should be compatible with pre-C++11 code.
2015-11-02 13:51:45 -05:00
David Neto
445ce4401d Add operand type for extension instruction number
This is required to support extended instructions that
have literal numbers as operands.  An example is OpenCL's
vloadn.

The previous code in the assembler assumed that *any* literal
number argument in any part of an OpExtInst must be the name
of the extended instruction.  That's true only for the first
literal number argument.
2015-10-26 12:55:33 -04:00
David Neto
21c4ad4b22 Add OpenCL extended instructions.
Versions 1.2, 2.0, and 2.1 all use the same
extended instruction list.

Updated the source code patch for the SPIR-V doc generator,
so it can both generate the core syntax table, and also the
OpenCL extended instructions table.

Tested the Math and Common functions.
TODO: test the remaining entries.
2015-10-26 12:55:33 -04:00
Lei Zhang
6483bd7132 Enforce suitable literal number operands to be unsigned integers.
Except for OpConstant and OpSpecConstant, all other literal number
operands are indeed unsigned integers. So,

* Rename all *LITERAL_NUMBER* operand types to *LITERAL_INTEGER*.
* Expect unsigned integers for *LITERAL_INTEGER* operands.
* Keep MULITPLE_WORD_LITERAL untouched since it is only used by
  OpConstant and OpSpecConstant.

And we want to provide the capability to specify floating-point
numbers after !<integer> in the alternate parsing mode. So,
OPTIONAL_LITERAL_NUMBER is reserved for OPTIONAL_CIV.
2015-10-26 12:55:33 -04:00
Andrew Woloszyn
537e77663d Added tracking to types and validated certain instructions.
We need to know how to generate correct SPIRV for cases like
OpConstant %int64 42 since the current parser will encode the 42 as a
32-bit value incorrectly.

This change is the first of a pair. This one tracks types, and makes
sure that OpConstant and OpSpecConstant are only ever called with
Integer or Float types, and OpSwitch is only called with integer
generating values.
2015-10-26 12:55:33 -04:00
David Neto
9db3a53897 Remove spv_opcode_flags_t and flags fields.
The flags fields in both spv_opcode_desc_t and spv_operand_desc_t
are redundant with the capabilities mask field in the same
structure.
2015-10-26 12:55:33 -04:00
David Neto
f6b865110c Accept long UTF-8 Literal Strings 2015-10-26 12:55:33 -04:00
David Neto
b5dc8fcd5d Support strings with up to 65535 chars, and null.
Move the definition of spv_instruction_t to an internal
header file, since it now depends on C++ and is not
used by the external interface.

Use a std::vector<uint32_t> in spv_instruction_t
instead of a fixed size array.
2015-10-26 12:55:33 -04:00
David Neto
8b19f27026 Define spv_capability_mask_t for readability. 2015-10-26 12:55:33 -04:00
David Neto
1b9d70a317 Test capabilities for enums sections 3.21-3.31
Fixes dependencies among capabilities.  (The table should store
the mask of capabilites, not the capability enum.)

Remove the old spot check test for capabilities of enums.
2015-10-26 12:55:33 -04:00
David Neto
ddda85a5c5 Fix capabilities for enums in Rev32, sec 3.3-3.20 2015-10-26 12:55:33 -04:00
Dejan Mircevski
4170ceca12 Create spv_language_capabilities_t and widen capabilities fields.
If this is acceptable, I'll do a wholesale switch of operand and opcode
definitions to capability bitfields.
2015-10-26 12:55:33 -04:00
Dejan Mircevski
50babb2d00 Run clang-format. 2015-10-26 12:55:33 -04:00
Dejan Mircevski
903f9d6b70 Implement alternate-parsing mode for !<integer>. 2015-10-26 12:55:33 -04:00
David Neto
561dc4e975 Remove SPV_OPERAND_TYPE_LITERAL
All uses of OptionalLiteral by the SPIR-V spec are used
for literal numbers.

Also rename:
- SPV_OPERAND_TYPE_OPTIONAL_LITERAL to
  SPV_OPERAND_TYPE_OPTIONAL_LITERAL_NUMBER.
- SPV_OPERAND_TYPE_VARIABLE_LITERAL to
  SPV_OPERAND_TYPE_VARIABLE_LITERAL_NUMBER.
- SPV_OPERAND_TYPE_VARIABLE_LITERAL_ID to
  SPV_OPERAND_TYPE_VARIABLE_LITERAL_NUMBER_ID.
- SPV_OPERAND_TYPE_VARIABLE_ID_LITERAL to
  SPV_OPERAND_TYPE_VARIABLE_ID_LITERAL_NUMBER.
- SPV_OPERAND_TYPE_LITERAL_IN_OPTIONAL_TUPLE to
  SPV_OPERAND_TYPE_LITERAL_NUMBER_IN_OPTIONAL_TUPLE.
2015-10-26 12:55:33 -04:00