blob: e0269589353132d630e21bafb8e332992025242b [file] [log] [blame]
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<!--[if IE]><meta http-equiv="X-UA-Compatible" content="IE=edge"><![endif]-->
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<meta name="generator" content="Asciidoctor 1.5.8">
<meta name="author" content="Khronos&#174; OpenCL Working Group">
<title>The OpenCL&#8482; SPIR-V Environment Specification</title>
<style>
/*! normalize.css v2.1.2 | MIT License | git.io/normalize */
/* ========================================================================== HTML5 display definitions ========================================================================== */
/** Correct `block` display not defined in IE 8/9. */
article, aside, details, figcaption, figure, footer, header, hgroup, main, nav, section, summary { display: block; }
/** Correct `inline-block` display not defined in IE 8/9. */
audio, canvas, video { display: inline-block; }
/** Prevent modern browsers from displaying `audio` without controls. Remove excess height in iOS 5 devices. */
audio:not([controls]) { display: none; height: 0; }
/** Address `[hidden]` styling not present in IE 8/9. Hide the `template` element in IE, Safari, and Firefox < 22. */
[hidden], template { display: none; }
script { display: none !important; }
/* ========================================================================== Base ========================================================================== */
/** 1. Set default font family to sans-serif. 2. Prevent iOS text size adjust after orientation change, without disabling user zoom. */
html { font-family: sans-serif; /* 1 */ -ms-text-size-adjust: 100%; /* 2 */ -webkit-text-size-adjust: 100%; /* 2 */ }
/** Remove default margin. */
body { margin: 0; }
/* ========================================================================== Links ========================================================================== */
/** Remove the gray background color from active links in IE 10. */
a { background: transparent; }
/** Address `outline` inconsistency between Chrome and other browsers. */
a:focus { outline: thin dotted; }
/** Improve readability when focused and also mouse hovered in all browsers. */
a:active, a:hover { outline: 0; }
/* ========================================================================== Typography ========================================================================== */
/** Address variable `h1` font-size and margin within `section` and `article` contexts in Firefox 4+, Safari 5, and Chrome. */
h1 { font-size: 2em; margin: 0.67em 0; }
/** Address styling not present in IE 8/9, Safari 5, and Chrome. */
abbr[title] { border-bottom: 1px dotted; }
/** Address style set to `bolder` in Firefox 4+, Safari 5, and Chrome. */
b, strong { font-weight: bold; }
/** Address styling not present in Safari 5 and Chrome. */
dfn { font-style: italic; }
/** Address differences between Firefox and other browsers. */
hr { -moz-box-sizing: content-box; box-sizing: content-box; height: 0; }
/** Address styling not present in IE 8/9. */
mark { background: #ff0; color: #000; }
/** Correct font family set oddly in Safari 5 and Chrome. */
code, kbd, pre, samp { font-family: monospace, serif; font-size: 1em; }
/** Improve readability of pre-formatted text in all browsers. */
pre { white-space: pre-wrap; }
/** Set consistent quote types. */
q { quotes: "\201C" "\201D" "\2018" "\2019"; }
/** Address inconsistent and variable font size in all browsers. */
small { font-size: 80%; }
/** Prevent `sub` and `sup` affecting `line-height` in all browsers. */
sub, sup { font-size: 75%; line-height: 0; position: relative; vertical-align: baseline; }
sup { top: -0.5em; }
sub { bottom: -0.25em; }
/* ========================================================================== Embedded content ========================================================================== */
/** Remove border when inside `a` element in IE 8/9. */
img { border: 0; }
/** Correct overflow displayed oddly in IE 9. */
svg:not(:root) { overflow: hidden; }
/* ========================================================================== Figures ========================================================================== */
/** Address margin not present in IE 8/9 and Safari 5. */
figure { margin: 0; }
/* ========================================================================== Forms ========================================================================== */
/** Define consistent border, margin, and padding. */
fieldset { border: 1px solid #c0c0c0; margin: 0 2px; padding: 0.35em 0.625em 0.75em; }
/** 1. Correct `color` not being inherited in IE 8/9. 2. Remove padding so people aren't caught out if they zero out fieldsets. */
legend { border: 0; /* 1 */ padding: 0; /* 2 */ }
/** 1. Correct font family not being inherited in all browsers. 2. Correct font size not being inherited in all browsers. 3. Address margins set differently in Firefox 4+, Safari 5, and Chrome. */
button, input, select, textarea { font-family: inherit; /* 1 */ font-size: 100%; /* 2 */ margin: 0; /* 3 */ }
/** Address Firefox 4+ setting `line-height` on `input` using `!important` in the UA stylesheet. */
button, input { line-height: normal; }
/** Address inconsistent `text-transform` inheritance for `button` and `select`. All other form control elements do not inherit `text-transform` values. Correct `button` style inheritance in Chrome, Safari 5+, and IE 8+. Correct `select` style inheritance in Firefox 4+ and Opera. */
button, select { text-transform: none; }
/** 1. Avoid the WebKit bug in Android 4.0.* where (2) destroys native `audio` and `video` controls. 2. Correct inability to style clickable `input` types in iOS. 3. Improve usability and consistency of cursor style between image-type `input` and others. */
button, html input[type="button"], input[type="reset"], input[type="submit"] { -webkit-appearance: button; /* 2 */ cursor: pointer; /* 3 */ }
/** Re-set default cursor for disabled elements. */
button[disabled], html input[disabled] { cursor: default; }
/** 1. Address box sizing set to `content-box` in IE 8/9. 2. Remove excess padding in IE 8/9. */
input[type="checkbox"], input[type="radio"] { box-sizing: border-box; /* 1 */ padding: 0; /* 2 */ }
/** 1. Address `appearance` set to `searchfield` in Safari 5 and Chrome. 2. Address `box-sizing` set to `border-box` in Safari 5 and Chrome (include `-moz` to future-proof). */
input[type="search"] { -webkit-appearance: textfield; /* 1 */ -moz-box-sizing: content-box; -webkit-box-sizing: content-box; /* 2 */ box-sizing: content-box; }
/** Remove inner padding and search cancel button in Safari 5 and Chrome on OS X. */
input[type="search"]::-webkit-search-cancel-button, input[type="search"]::-webkit-search-decoration { -webkit-appearance: none; }
/** Remove inner padding and border in Firefox 4+. */
button::-moz-focus-inner, input::-moz-focus-inner { border: 0; padding: 0; }
/** 1. Remove default vertical scrollbar in IE 8/9. 2. Improve readability and alignment in all browsers. */
textarea { overflow: auto; /* 1 */ vertical-align: top; /* 2 */ }
/* ========================================================================== Tables ========================================================================== */
/** Remove most spacing between table cells. */
table { border-collapse: collapse; border-spacing: 0; }
meta.foundation-mq-small { font-family: "only screen and (min-width: 768px)"; width: 768px; }
meta.foundation-mq-medium { font-family: "only screen and (min-width:1280px)"; width: 1280px; }
meta.foundation-mq-large { font-family: "only screen and (min-width:1440px)"; width: 1440px; }
*, *:before, *:after { -moz-box-sizing: border-box; -webkit-box-sizing: border-box; box-sizing: border-box; }
html, body { font-size: 100%; }
body { background: white; color: #222222; padding: 0; margin: 0; font-family: "Helvetica Neue", "Helvetica", Helvetica, Arial, sans-serif; font-weight: normal; font-style: normal; line-height: 1; position: relative; cursor: auto; }
a:hover { cursor: pointer; }
img, object, embed { max-width: 100%; height: auto; }
object, embed { height: 100%; }
img { -ms-interpolation-mode: bicubic; }
#map_canvas img, #map_canvas embed, #map_canvas object, .map_canvas img, .map_canvas embed, .map_canvas object { max-width: none !important; }
.left { float: left !important; }
.right { float: right !important; }
.text-left { text-align: left !important; }
.text-right { text-align: right !important; }
.text-center { text-align: center !important; }
.text-justify { text-align: justify !important; }
.hide { display: none; }
.antialiased { -webkit-font-smoothing: antialiased; }
img { display: inline-block; vertical-align: middle; }
textarea { height: auto; min-height: 50px; }
select { width: 100%; }
object, svg { display: inline-block; vertical-align: middle; }
.center { margin-left: auto; margin-right: auto; }
.spread { width: 100%; }
p.lead, .paragraph.lead > p, #preamble > .sectionbody > .paragraph:first-of-type p { font-size: 1.21875em; line-height: 1.6; }
.subheader, .admonitionblock td.content > .title, .audioblock > .title, .exampleblock > .title, .imageblock > .title, .listingblock > .title, .literalblock > .title, .stemblock > .title, .openblock > .title, .paragraph > .title, .quoteblock > .title, table.tableblock > .title, .verseblock > .title, .videoblock > .title, .dlist > .title, .olist > .title, .ulist > .title, .qlist > .title, .hdlist > .title { line-height: 1.4; color: black; font-weight: 300; margin-top: 0.2em; margin-bottom: 0.5em; }
/* Typography resets */
div, dl, dt, dd, ul, ol, li, h1, h2, h3, #toctitle, .sidebarblock > .content > .title, h4, h5, h6, pre, form, p, blockquote, th, td { margin: 0; padding: 0; direction: ltr; }
/* Default Link Styles */
a { color: #0068b0; text-decoration: none; line-height: inherit; }
a:hover, a:focus { color: #333333; }
a img { border: none; }
/* Default paragraph styles */
p { font-family: Noto, sans-serif; font-weight: normal; font-size: 1em; line-height: 1.6; margin-bottom: 0.75em; text-rendering: optimizeLegibility; }
p aside { font-size: 0.875em; line-height: 1.35; font-style: italic; }
/* Default header styles */
h1, h2, h3, #toctitle, .sidebarblock > .content > .title, h4, h5, h6 { font-family: Noto, sans-serif; font-weight: normal; font-style: normal; color: black; text-rendering: optimizeLegibility; margin-top: 0.5em; margin-bottom: 0.5em; line-height: 1.2125em; }
h1 small, h2 small, h3 small, #toctitle small, .sidebarblock > .content > .title small, h4 small, h5 small, h6 small { font-size: 60%; color: #4d4d4d; line-height: 0; }
h1 { font-size: 2.125em; }
h2 { font-size: 1.6875em; }
h3, #toctitle, .sidebarblock > .content > .title { font-size: 1.375em; }
h4 { font-size: 1.125em; }
h5 { font-size: 1.125em; }
h6 { font-size: 1em; }
hr { border: solid #dddddd; border-width: 1px 0 0; clear: both; margin: 1.25em 0 1.1875em; height: 0; }
/* Helpful Typography Defaults */
em, i { font-style: italic; line-height: inherit; }
strong, b { font-weight: bold; line-height: inherit; }
small { font-size: 60%; line-height: inherit; }
code { font-family: Consolas, "Liberation Mono", Courier, monospace; font-weight: normal; color: #264357; }
/* Lists */
ul, ol, dl { font-size: 1em; line-height: 1.6; margin-bottom: 0.75em; list-style-position: outside; font-family: Noto, sans-serif; }
ul, ol { margin-left: 1.5em; }
ul.no-bullet, ol.no-bullet { margin-left: 1.5em; }
/* Unordered Lists */
ul li ul, ul li ol { margin-left: 1.25em; margin-bottom: 0; font-size: 1em; /* Override nested font-size change */ }
ul.square li ul, ul.circle li ul, ul.disc li ul { list-style: inherit; }
ul.square { list-style-type: square; }
ul.circle { list-style-type: circle; }
ul.disc { list-style-type: disc; }
ul.no-bullet { list-style: none; }
/* Ordered Lists */
ol li ul, ol li ol { margin-left: 1.25em; margin-bottom: 0; }
/* Definition Lists */
dl dt { margin-bottom: 0.3em; font-weight: bold; }
dl dd { margin-bottom: 0.75em; }
/* Abbreviations */
abbr, acronym { text-transform: uppercase; font-size: 90%; color: black; border-bottom: 1px dotted #dddddd; cursor: help; }
abbr { text-transform: none; }
/* Blockquotes */
blockquote { margin: 0 0 0.75em; padding: 0.5625em 1.25em 0 1.1875em; border-left: 1px solid #dddddd; }
blockquote cite { display: block; font-size: 0.8125em; color: #5e93b8; }
blockquote cite:before { content: "\2014 \0020"; }
blockquote cite a, blockquote cite a:visited { color: #5e93b8; }
blockquote, blockquote p { line-height: 1.6; color: #333333; }
/* Microformats */
.vcard { display: inline-block; margin: 0 0 1.25em 0; border: 1px solid #dddddd; padding: 0.625em 0.75em; }
.vcard li { margin: 0; display: block; }
.vcard .fn { font-weight: bold; font-size: 0.9375em; }
.vevent .summary { font-weight: bold; }
.vevent abbr { cursor: auto; text-decoration: none; font-weight: bold; border: none; padding: 0 0.0625em; }
@media only screen and (min-width: 768px) { h1, h2, h3, #toctitle, .sidebarblock > .content > .title, h4, h5, h6 { line-height: 1.4; }
h1 { font-size: 2.75em; }
h2 { font-size: 2.3125em; }
h3, #toctitle, .sidebarblock > .content > .title { font-size: 1.6875em; }
h4 { font-size: 1.4375em; } }
/* Tables */
table { background: white; margin-bottom: 1.25em; border: solid 1px #d8d8ce; }
table thead, table tfoot { background: -webkit-linear-gradient(top, #add386, #90b66a); font-weight: bold; }
table thead tr th, table thead tr td, table tfoot tr th, table tfoot tr td { padding: 0.5em 0.625em 0.625em; font-size: inherit; color: white; text-align: left; }
table tr th, table tr td { padding: 0.5625em 0.625em; font-size: inherit; color: #6d6e71; }
table tr.even, table tr.alt, table tr:nth-of-type(even) { background: #edf2f2; }
table thead tr th, table tfoot tr th, table tbody tr td, table tr td, table tfoot tr td { display: table-cell; line-height: 1.4; }
body { -moz-osx-font-smoothing: grayscale; -webkit-font-smoothing: antialiased; tab-size: 4; }
h1, h2, h3, #toctitle, .sidebarblock > .content > .title, h4, h5, h6 { line-height: 1.4; }
a:hover, a:focus { text-decoration: underline; }
.clearfix:before, .clearfix:after, .float-group:before, .float-group:after { content: " "; display: table; }
.clearfix:after, .float-group:after { clear: both; }
*:not(pre) > code { font-size: inherit; font-style: normal !important; letter-spacing: 0; padding: 0; background-color: white; -webkit-border-radius: 0; border-radius: 0; line-height: inherit; word-wrap: break-word; }
*:not(pre) > code.nobreak { word-wrap: normal; }
*:not(pre) > code.nowrap { white-space: nowrap; }
pre, pre > code { line-height: 1.6; color: #264357; font-family: Consolas, "Liberation Mono", Courier, monospace; font-weight: normal; }
em em { font-style: normal; }
strong strong { font-weight: normal; }
.keyseq { color: #333333; }
kbd { font-family: Consolas, "Liberation Mono", Courier, monospace; display: inline-block; color: black; font-size: 0.65em; line-height: 1.45; background-color: #f7f7f7; border: 1px solid #ccc; -webkit-border-radius: 3px; border-radius: 3px; -webkit-box-shadow: 0 1px 0 rgba(0, 0, 0, 0.2), 0 0 0 0.1em white inset; box-shadow: 0 1px 0 rgba(0, 0, 0, 0.2), 0 0 0 0.1em white inset; margin: 0 0.15em; padding: 0.2em 0.5em; vertical-align: middle; position: relative; top: -0.1em; white-space: nowrap; }
.keyseq kbd:first-child { margin-left: 0; }
.keyseq kbd:last-child { margin-right: 0; }
.menuseq, .menuref { color: #000; }
.menuseq b:not(.caret), .menuref { font-weight: inherit; }
.menuseq { word-spacing: -0.02em; }
.menuseq b.caret { font-size: 1.25em; line-height: 0.8; }
.menuseq i.caret { font-weight: bold; text-align: center; width: 0.45em; }
b.button:before, b.button:after { position: relative; top: -1px; font-weight: normal; }
b.button:before { content: "["; padding: 0 3px 0 2px; }
b.button:after { content: "]"; padding: 0 2px 0 3px; }
#header, #content, #footnotes, #footer { width: 100%; margin-left: auto; margin-right: auto; margin-top: 0; margin-bottom: 0; max-width: 62.5em; *zoom: 1; position: relative; padding-left: 1.5em; padding-right: 1.5em; }
#header:before, #header:after, #content:before, #content:after, #footnotes:before, #footnotes:after, #footer:before, #footer:after { content: " "; display: table; }
#header:after, #content:after, #footnotes:after, #footer:after { clear: both; }
#content { margin-top: 1.25em; }
#content:before { content: none; }
#header > h1:first-child { color: black; margin-top: 2.25rem; margin-bottom: 0; }
#header > h1:first-child + #toc { margin-top: 8px; border-top: 1px solid #dddddd; }
#header > h1:only-child, body.toc2 #header > h1:nth-last-child(2) { border-bottom: 1px solid #dddddd; padding-bottom: 8px; }
#header .details { border-bottom: 1px solid #dddddd; line-height: 1.45; padding-top: 0.25em; padding-bottom: 0.25em; padding-left: 0.25em; color: #5e93b8; display: -ms-flexbox; display: -webkit-flex; display: flex; -ms-flex-flow: row wrap; -webkit-flex-flow: row wrap; flex-flow: row wrap; }
#header .details span:first-child { margin-left: -0.125em; }
#header .details span.email a { color: #333333; }
#header .details br { display: none; }
#header .details br + span:before { content: "\00a0\2013\00a0"; }
#header .details br + span.author:before { content: "\00a0\22c5\00a0"; color: #333333; }
#header .details br + span#revremark:before { content: "\00a0|\00a0"; }
#header #revnumber { text-transform: capitalize; }
#header #revnumber:after { content: "\00a0"; }
#content > h1:first-child:not([class]) { color: black; border-bottom: 1px solid #dddddd; padding-bottom: 8px; margin-top: 0; padding-top: 1rem; margin-bottom: 1.25rem; }
#toc { border-bottom: 0 solid #dddddd; padding-bottom: 0.5em; }
#toc > ul { margin-left: 0.125em; }
#toc ul.sectlevel0 > li > a { font-style: italic; }
#toc ul.sectlevel0 ul.sectlevel1 { margin: 0.5em 0; }
#toc ul { font-family: Noto, sans-serif; list-style-type: none; }
#toc li { line-height: 1.3334; margin-top: 0.3334em; }
#toc a { text-decoration: none; }
#toc a:active { text-decoration: underline; }
#toctitle { color: black; font-size: 1.2em; }
@media only screen and (min-width: 768px) { #toctitle { font-size: 1.375em; }
body.toc2 { padding-left: 15em; padding-right: 0; }
#toc.toc2 { margin-top: 0 !important; background-color: white; position: fixed; width: 15em; left: 0; top: 0; border-right: 1px solid #dddddd; border-top-width: 0 !important; border-bottom-width: 0 !important; z-index: 1000; padding: 1.25em 1em; height: 100%; overflow: auto; }
#toc.toc2 #toctitle { margin-top: 0; margin-bottom: 0.8rem; font-size: 1.2em; }
#toc.toc2 > ul { font-size: 0.9em; margin-bottom: 0; }
#toc.toc2 ul ul { margin-left: 0; padding-left: 1em; }
#toc.toc2 ul.sectlevel0 ul.sectlevel1 { padding-left: 0; margin-top: 0.5em; margin-bottom: 0.5em; }
body.toc2.toc-right { padding-left: 0; padding-right: 15em; }
body.toc2.toc-right #toc.toc2 { border-right-width: 0; border-left: 1px solid #dddddd; left: auto; right: 0; } }
@media only screen and (min-width: 1280px) { body.toc2 { padding-left: 20em; padding-right: 0; }
#toc.toc2 { width: 20em; }
#toc.toc2 #toctitle { font-size: 1.375em; }
#toc.toc2 > ul { font-size: 0.95em; }
#toc.toc2 ul ul { padding-left: 1.25em; }
body.toc2.toc-right { padding-left: 0; padding-right: 20em; } }
#content #toc { border-style: solid; border-width: 1px; border-color: #e6e6e6; margin-bottom: 1.25em; padding: 1.25em; background: white; -webkit-border-radius: 0; border-radius: 0; }
#content #toc > :first-child { margin-top: 0; }
#content #toc > :last-child { margin-bottom: 0; }
#footer { max-width: 100%; background-color: none; padding: 1.25em; }
#footer-text { color: black; line-height: 1.44; }
#content { margin-bottom: 0.625em; }
.sect1 { padding-bottom: 0.625em; }
@media only screen and (min-width: 768px) { #content { margin-bottom: 1.25em; }
.sect1 { padding-bottom: 1.25em; } }
.sect1:last-child { padding-bottom: 0; }
.sect1 + .sect1 { border-top: 0 solid #dddddd; }
#content h1 > a.anchor, h2 > a.anchor, h3 > a.anchor, #toctitle > a.anchor, .sidebarblock > .content > .title > a.anchor, h4 > a.anchor, h5 > a.anchor, h6 > a.anchor { position: absolute; z-index: 1001; width: 1.5ex; margin-left: -1.5ex; display: block; text-decoration: none !important; visibility: hidden; text-align: center; font-weight: normal; }
#content h1 > a.anchor:before, h2 > a.anchor:before, h3 > a.anchor:before, #toctitle > a.anchor:before, .sidebarblock > .content > .title > a.anchor:before, h4 > a.anchor:before, h5 > a.anchor:before, h6 > a.anchor:before { content: "\00A7"; font-size: 0.85em; display: block; padding-top: 0.1em; }
#content h1:hover > a.anchor, #content h1 > a.anchor:hover, h2:hover > a.anchor, h2 > a.anchor:hover, h3:hover > a.anchor, #toctitle:hover > a.anchor, .sidebarblock > .content > .title:hover > a.anchor, h3 > a.anchor:hover, #toctitle > a.anchor:hover, .sidebarblock > .content > .title > a.anchor:hover, h4:hover > a.anchor, h4 > a.anchor:hover, h5:hover > a.anchor, h5 > a.anchor:hover, h6:hover > a.anchor, h6 > a.anchor:hover { visibility: visible; }
#content h1 > a.link, h2 > a.link, h3 > a.link, #toctitle > a.link, .sidebarblock > .content > .title > a.link, h4 > a.link, h5 > a.link, h6 > a.link { color: black; text-decoration: none; }
#content h1 > a.link:hover, h2 > a.link:hover, h3 > a.link:hover, #toctitle > a.link:hover, .sidebarblock > .content > .title > a.link:hover, h4 > a.link:hover, h5 > a.link:hover, h6 > a.link:hover { color: black; }
.audioblock, .imageblock, .literalblock, .listingblock, .stemblock, .videoblock { margin-bottom: 1.25em; }
.admonitionblock td.content > .title, .audioblock > .title, .exampleblock > .title, .imageblock > .title, .listingblock > .title, .literalblock > .title, .stemblock > .title, .openblock > .title, .paragraph > .title, .quoteblock > .title, table.tableblock > .title, .verseblock > .title, .videoblock > .title, .dlist > .title, .olist > .title, .ulist > .title, .qlist > .title, .hdlist > .title { text-rendering: optimizeLegibility; text-align: left; }
table.tableblock > caption.title { white-space: nowrap; overflow: visible; max-width: 0; }
.paragraph.lead > p, #preamble > .sectionbody > .paragraph:first-of-type p { color: black; }
table.tableblock #preamble > .sectionbody > .paragraph:first-of-type p { font-size: inherit; }
.admonitionblock > table { border-collapse: separate; border: 0; background: none; width: 100%; }
.admonitionblock > table td.icon { text-align: center; width: 80px; }
.admonitionblock > table td.icon img { max-width: initial; }
.admonitionblock > table td.icon .title { font-weight: bold; font-family: Noto, sans-serif; text-transform: uppercase; }
.admonitionblock > table td.content { padding-left: 1.125em; padding-right: 1.25em; border-left: 1px solid #dddddd; color: #5e93b8; }
.admonitionblock > table td.content > :last-child > :last-child { margin-bottom: 0; }
.exampleblock > .content { border-style: solid; border-width: 1px; border-color: #e6e6e6; margin-bottom: 1.25em; padding: 1.25em; background: white; -webkit-border-radius: 0; border-radius: 0; }
.exampleblock > .content > :first-child { margin-top: 0; }
.exampleblock > .content > :last-child { margin-bottom: 0; }
.sidebarblock { border-style: solid; border-width: 1px; border-color: #e6e6e6; margin-bottom: 1.25em; padding: 1.25em; background: white; -webkit-border-radius: 0; border-radius: 0; }
.sidebarblock > :first-child { margin-top: 0; }
.sidebarblock > :last-child { margin-bottom: 0; }
.sidebarblock > .content > .title { color: black; margin-top: 0; }
.exampleblock > .content > :last-child > :last-child, .exampleblock > .content .olist > ol > li:last-child > :last-child, .exampleblock > .content .ulist > ul > li:last-child > :last-child, .exampleblock > .content .qlist > ol > li:last-child > :last-child, .sidebarblock > .content > :last-child > :last-child, .sidebarblock > .content .olist > ol > li:last-child > :last-child, .sidebarblock > .content .ulist > ul > li:last-child > :last-child, .sidebarblock > .content .qlist > ol > li:last-child > :last-child { margin-bottom: 0; }
.literalblock pre, .listingblock pre:not(.highlight), .listingblock pre[class="highlight"], .listingblock pre[class^="highlight "], .listingblock pre.CodeRay, .listingblock pre.prettyprint { background: #eeeeee; }
.sidebarblock .literalblock pre, .sidebarblock .listingblock pre:not(.highlight), .sidebarblock .listingblock pre[class="highlight"], .sidebarblock .listingblock pre[class^="highlight "], .sidebarblock .listingblock pre.CodeRay, .sidebarblock .listingblock pre.prettyprint { background: #f2f1f1; }
.literalblock pre, .literalblock pre[class], .listingblock pre, .listingblock pre[class] { border: 1px hidden #666666; -webkit-border-radius: 0; border-radius: 0; word-wrap: break-word; padding: 1.25em 1.5625em 1.125em 1.5625em; font-size: 0.8125em; }
.literalblock pre.nowrap, .literalblock pre[class].nowrap, .listingblock pre.nowrap, .listingblock pre[class].nowrap { overflow-x: auto; white-space: pre; word-wrap: normal; }
@media only screen and (min-width: 768px) { .literalblock pre, .literalblock pre[class], .listingblock pre, .listingblock pre[class] { font-size: 0.90625em; } }
@media only screen and (min-width: 1280px) { .literalblock pre, .literalblock pre[class], .listingblock pre, .listingblock pre[class] { font-size: 1em; } }
.literalblock.output pre { color: #eeeeee; background-color: #264357; }
.listingblock pre.highlightjs { padding: 0; }
.listingblock pre.highlightjs > code { padding: 1.25em 1.5625em 1.125em 1.5625em; -webkit-border-radius: 0; border-radius: 0; }
.listingblock > .content { position: relative; }
.listingblock code[data-lang]:before { display: none; content: attr(data-lang); position: absolute; font-size: 0.75em; top: 0.425rem; right: 0.5rem; line-height: 1; text-transform: uppercase; color: #999; }
.listingblock:hover code[data-lang]:before { display: block; }
.listingblock.terminal pre .command:before { content: attr(data-prompt); padding-right: 0.5em; color: #999; }
.listingblock.terminal pre .command:not([data-prompt]):before { content: "$"; }
table.pyhltable { border-collapse: separate; border: 0; margin-bottom: 0; background: none; }
table.pyhltable td { vertical-align: top; padding-top: 0; padding-bottom: 0; line-height: 1.6; }
table.pyhltable td.code { padding-left: .75em; padding-right: 0; }
pre.pygments .lineno, table.pyhltable td:not(.code) { color: #999; padding-left: 0; padding-right: .5em; border-right: 1px solid #dddddd; }
pre.pygments .lineno { display: inline-block; margin-right: .25em; }
table.pyhltable .linenodiv { background: none !important; padding-right: 0 !important; }
.quoteblock { margin: 0 1em 0.75em 1.5em; display: table; }
.quoteblock > .title { margin-left: -1.5em; margin-bottom: 0.75em; }
.quoteblock blockquote, .quoteblock blockquote p { color: #333333; font-size: 1.15rem; line-height: 1.75; word-spacing: 0.1em; letter-spacing: 0; font-style: italic; text-align: justify; }
.quoteblock blockquote { margin: 0; padding: 0; border: 0; }
.quoteblock blockquote:before { content: "\201c"; float: left; font-size: 2.75em; font-weight: bold; line-height: 0.6em; margin-left: -0.6em; color: black; text-shadow: 0 1px 2px rgba(0, 0, 0, 0.1); }
.quoteblock blockquote > .paragraph:last-child p { margin-bottom: 0; }
.quoteblock .attribution { margin-top: 0.5em; margin-right: 0.5ex; text-align: right; }
.quoteblock .quoteblock { margin-left: 0; margin-right: 0; padding: 0.5em 0; border-left: 3px solid #5e93b8; }
.quoteblock .quoteblock blockquote { padding: 0 0 0 0.75em; }
.quoteblock .quoteblock blockquote:before { display: none; }
.verseblock { margin: 0 1em 0.75em 1em; }
.verseblock pre { font-family: "Open Sans", "DejaVu Sans", sans; font-size: 1.15rem; color: #333333; font-weight: 300; text-rendering: optimizeLegibility; }
.verseblock pre strong { font-weight: 400; }
.verseblock .attribution { margin-top: 1.25rem; margin-left: 0.5ex; }
.quoteblock .attribution, .verseblock .attribution { font-size: 0.8125em; line-height: 1.45; font-style: italic; }
.quoteblock .attribution br, .verseblock .attribution br { display: none; }
.quoteblock .attribution cite, .verseblock .attribution cite { display: block; letter-spacing: -0.025em; color: #5e93b8; }
.quoteblock.abstract { margin: 0 0 0.75em 0; display: block; }
.quoteblock.abstract blockquote, .quoteblock.abstract blockquote p { text-align: left; word-spacing: 0; }
.quoteblock.abstract blockquote:before, .quoteblock.abstract blockquote p:first-of-type:before { display: none; }
table.tableblock { max-width: 100%; border-collapse: separate; }
table.tableblock td > .paragraph:last-child p > p:last-child, table.tableblock th > p:last-child, table.tableblock td > p:last-child { margin-bottom: 0; }
table.tableblock, th.tableblock, td.tableblock { border: 0 solid #d8d8ce; }
table.grid-all > thead > tr > .tableblock, table.grid-all > tbody > tr > .tableblock { border-width: 0 1px 1px 0; }
table.grid-all > tfoot > tr > .tableblock { border-width: 1px 1px 0 0; }
table.grid-cols > * > tr > .tableblock { border-width: 0 1px 0 0; }
table.grid-rows > thead > tr > .tableblock, table.grid-rows > tbody > tr > .tableblock { border-width: 0 0 1px 0; }
table.grid-rows > tfoot > tr > .tableblock { border-width: 1px 0 0 0; }
table.grid-all > * > tr > .tableblock:last-child, table.grid-cols > * > tr > .tableblock:last-child { border-right-width: 0; }
table.grid-all > tbody > tr:last-child > .tableblock, table.grid-all > thead:last-child > tr > .tableblock, table.grid-rows > tbody > tr:last-child > .tableblock, table.grid-rows > thead:last-child > tr > .tableblock { border-bottom-width: 0; }
table.frame-all { border-width: 1px; }
table.frame-sides { border-width: 0 1px; }
table.frame-topbot { border-width: 1px 0; }
th.halign-left, td.halign-left { text-align: left; }
th.halign-right, td.halign-right { text-align: right; }
th.halign-center, td.halign-center { text-align: center; }
th.valign-top, td.valign-top { vertical-align: top; }
th.valign-bottom, td.valign-bottom { vertical-align: bottom; }
th.valign-middle, td.valign-middle { vertical-align: middle; }
table thead th, table tfoot th { font-weight: bold; }
tbody tr th { display: table-cell; line-height: 1.4; background: -webkit-linear-gradient(top, #add386, #90b66a); }
tbody tr th, tbody tr th p, tfoot tr th, tfoot tr th p { color: white; font-weight: bold; }
p.tableblock > code:only-child { background: none; padding: 0; }
p.tableblock { font-size: 1em; }
td > div.verse { white-space: pre; }
ol { margin-left: 1.75em; }
ul li ol { margin-left: 1.5em; }
dl dd { margin-left: 1.125em; }
dl dd:last-child, dl dd:last-child > :last-child { margin-bottom: 0; }
ol > li p, ul > li p, ul dd, ol dd, .olist .olist, .ulist .ulist, .ulist .olist, .olist .ulist { margin-bottom: 0.375em; }
ul.checklist, ul.none, ol.none, ul.no-bullet, ol.no-bullet, ol.unnumbered, ul.unstyled, ol.unstyled { list-style-type: none; }
ul.no-bullet, ol.no-bullet, ol.unnumbered { margin-left: 0.625em; }
ul.unstyled, ol.unstyled { margin-left: 0; }
ul.checklist { margin-left: 0.625em; }
ul.checklist li > p:first-child > .fa-square-o:first-child, ul.checklist li > p:first-child > .fa-check-square-o:first-child { width: 1.25em; font-size: 0.8em; position: relative; bottom: 0.125em; }
ul.checklist li > p:first-child > input[type="checkbox"]:first-child { margin-right: 0.25em; }
ul.inline { display: -ms-flexbox; display: -webkit-box; display: flex; -ms-flex-flow: row wrap; -webkit-flex-flow: row wrap; flex-flow: row wrap; list-style: none; margin: 0 0 0.375em -0.75em; }
ul.inline > li { margin-left: 0.75em; }
.unstyled dl dt { font-weight: normal; font-style: normal; }
ol.arabic { list-style-type: decimal; }
ol.decimal { list-style-type: decimal-leading-zero; }
ol.loweralpha { list-style-type: lower-alpha; }
ol.upperalpha { list-style-type: upper-alpha; }
ol.lowerroman { list-style-type: lower-roman; }
ol.upperroman { list-style-type: upper-roman; }
ol.lowergreek { list-style-type: lower-greek; }
.hdlist > table, .colist > table { border: 0; background: none; }
.hdlist > table > tbody > tr, .colist > table > tbody > tr { background: none; }
td.hdlist1, td.hdlist2 { vertical-align: top; padding: 0 0.625em; }
td.hdlist1 { font-weight: bold; padding-bottom: 0.75em; }
.literalblock + .colist, .listingblock + .colist { margin-top: -0.5em; }
.colist > table tr > td:first-of-type { padding: 0.4em 0.75em 0 0.75em; line-height: 1; vertical-align: top; }
.colist > table tr > td:first-of-type img { max-width: initial; }
.colist > table tr > td:last-of-type { padding: 0.25em 0; }
.thumb, .th { line-height: 0; display: inline-block; border: solid 4px white; -webkit-box-shadow: 0 0 0 1px #dddddd; box-shadow: 0 0 0 1px #dddddd; }
.imageblock.left, .imageblock[style*="float: left"] { margin: 0.25em 0.625em 1.25em 0; }
.imageblock.right, .imageblock[style*="float: right"] { margin: 0.25em 0 1.25em 0.625em; }
.imageblock > .title { margin-bottom: 0; }
.imageblock.thumb, .imageblock.th { border-width: 6px; }
.imageblock.thumb > .title, .imageblock.th > .title { padding: 0 0.125em; }
.image.left, .image.right { margin-top: 0.25em; margin-bottom: 0.25em; display: inline-block; line-height: 0; }
.image.left { margin-right: 0.625em; }
.image.right { margin-left: 0.625em; }
a.image { text-decoration: none; display: inline-block; }
a.image object { pointer-events: none; }
sup.footnote, sup.footnoteref { font-size: 0.875em; position: static; vertical-align: super; }
sup.footnote a, sup.footnoteref a { text-decoration: none; }
sup.footnote a:active, sup.footnoteref a:active { text-decoration: underline; }
#footnotes { padding-top: 0.75em; padding-bottom: 0.75em; margin-bottom: 0.625em; }
#footnotes hr { width: 20%; min-width: 6.25em; margin: -0.25em 0 0.75em 0; border-width: 1px 0 0 0; }
#footnotes .footnote { padding: 0 0.375em 0 0.225em; line-height: 1.3334; font-size: 0.875em; margin-left: 1.2em; margin-bottom: 0.2em; }
#footnotes .footnote a:first-of-type { font-weight: bold; text-decoration: none; margin-left: -1.05em; }
#footnotes .footnote:last-of-type { margin-bottom: 0; }
#content #footnotes { margin-top: -0.625em; margin-bottom: 0; padding: 0.75em 0; }
.gist .file-data > table { border: 0; background: #fff; width: 100%; margin-bottom: 0; }
.gist .file-data > table td.line-data { width: 99%; }
div.unbreakable { page-break-inside: avoid; }
.big { font-size: larger; }
.small { font-size: smaller; }
.underline { text-decoration: underline; }
.overline { text-decoration: overline; }
.line-through { text-decoration: line-through; }
.aqua { color: #00bfbf; }
.aqua-background { background-color: #00fafa; }
.black { color: black; }
.black-background { background-color: black; }
.blue { color: #0000bf; }
.blue-background { background-color: #0000fa; }
.fuchsia { color: #bf00bf; }
.fuchsia-background { background-color: #fa00fa; }
.gray { color: #606060; }
.gray-background { background-color: #7d7d7d; }
.green { color: #006000; }
.green-background { background-color: #007d00; }
.lime { color: #00bf00; }
.lime-background { background-color: #00fa00; }
.maroon { color: #600000; }
.maroon-background { background-color: #7d0000; }
.navy { color: #000060; }
.navy-background { background-color: #00007d; }
.olive { color: #606000; }
.olive-background { background-color: #7d7d00; }
.purple { color: #600060; }
.purple-background { background-color: #7d007d; }
.red { color: #bf0000; }
.red-background { background-color: #fa0000; }
.silver { color: #909090; }
.silver-background { background-color: #bcbcbc; }
.teal { color: #006060; }
.teal-background { background-color: #007d7d; }
.white { color: #bfbfbf; }
.white-background { background-color: #fafafa; }
.yellow { color: #bfbf00; }
.yellow-background { background-color: #fafa00; }
span.icon > .fa { cursor: default; }
a span.icon > .fa { cursor: inherit; }
.admonitionblock td.icon [class^="fa icon-"] { font-size: 2.5em; text-shadow: 1px 1px 2px rgba(0, 0, 0, 0.5); cursor: default; }
.admonitionblock td.icon .icon-note:before { content: "\f05a"; color: #29475c; }
.admonitionblock td.icon .icon-tip:before { content: "\f0eb"; text-shadow: 1px 1px 2px rgba(155, 155, 0, 0.8); color: #111; }
.admonitionblock td.icon .icon-warning:before { content: "\f071"; color: #bf6900; }
.admonitionblock td.icon .icon-caution:before { content: "\f06d"; color: #bf3400; }
.admonitionblock td.icon .icon-important:before { content: "\f06a"; color: #bf0000; }
.conum[data-value] { display: inline-block; color: #fff !important; background-color: black; -webkit-border-radius: 100px; border-radius: 100px; text-align: center; font-size: 0.75em; width: 1.67em; height: 1.67em; line-height: 1.67em; font-family: "Open Sans", "DejaVu Sans", sans-serif; font-style: normal; font-weight: bold; }
.conum[data-value] * { color: #fff !important; }
.conum[data-value] + b { display: none; }
.conum[data-value]:after { content: attr(data-value); }
pre .conum[data-value] { position: relative; top: -0.125em; }
b.conum * { color: inherit !important; }
.conum:not([data-value]):empty { display: none; }
h1, h2, h3, #toctitle, .sidebarblock > .content > .title, h4, h5, h6 { border-bottom: 1px solid #dddddd; }
.sect1 { padding-bottom: 0; }
#toctitle { color: #00406F; font-weight: normal; margin-top: 1.5em; }
.sidebarblock { border-color: #aaa; }
code { -webkit-border-radius: 4px; border-radius: 4px; }
p.tableblock.header { color: #6d6e71; }
.literalblock pre, .listingblock pre { background: #eeeeee; }
</style>
<link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/font-awesome/4.7.0/css/font-awesome.min.css">
<style>
/* Stylesheet for CodeRay to match GitHub theme | MIT License | http://foundation.zurb.com */
/*pre.CodeRay {background-color:#f7f7f8;}*/
.CodeRay .line-numbers{border-right:1px solid #d8d8d8;padding:0 0.5em 0 .25em}
.CodeRay span.line-numbers{display:inline-block;margin-right:.5em;color:rgba(0,0,0,.3)}
.CodeRay .line-numbers strong{color:rgba(0,0,0,.4)}
table.CodeRay{border-collapse:separate;border-spacing:0;margin-bottom:0;border:0;background:none}
table.CodeRay td{vertical-align: top;line-height:1.45}
table.CodeRay td.line-numbers{text-align:right}
table.CodeRay td.line-numbers>pre{padding:0;color:rgba(0,0,0,.3)}
table.CodeRay td.code{padding:0 0 0 .5em}
table.CodeRay td.code>pre{padding:0}
.CodeRay .debug{color:#fff !important;background:#000080 !important}
.CodeRay .annotation{color:#007}
.CodeRay .attribute-name{color:#000080}
.CodeRay .attribute-value{color:#700}
.CodeRay .binary{color:#509}
.CodeRay .comment{color:#998;font-style:italic}
.CodeRay .char{color:#04d}
.CodeRay .char .content{color:#04d}
.CodeRay .char .delimiter{color:#039}
.CodeRay .class{color:#458;font-weight:bold}
.CodeRay .complex{color:#a08}
.CodeRay .constant,.CodeRay .predefined-constant{color:#008080}
.CodeRay .color{color:#099}
.CodeRay .class-variable{color:#369}
.CodeRay .decorator{color:#b0b}
.CodeRay .definition{color:#099}
.CodeRay .delimiter{color:#000}
.CodeRay .doc{color:#970}
.CodeRay .doctype{color:#34b}
.CodeRay .doc-string{color:#d42}
.CodeRay .escape{color:#666}
.CodeRay .entity{color:#800}
.CodeRay .error{color:#808}
.CodeRay .exception{color:inherit}
.CodeRay .filename{color:#099}
.CodeRay .function{color:#900;font-weight:bold}
.CodeRay .global-variable{color:#008080}
.CodeRay .hex{color:#058}
.CodeRay .integer,.CodeRay .float{color:#099}
.CodeRay .include{color:#555}
.CodeRay .inline{color:#000}
.CodeRay .inline .inline{background:#ccc}
.CodeRay .inline .inline .inline{background:#bbb}
.CodeRay .inline .inline-delimiter{color:#d14}
.CodeRay .inline-delimiter{color:#d14}
.CodeRay .important{color:#555;font-weight:bold}
.CodeRay .interpreted{color:#b2b}
.CodeRay .instance-variable{color:#008080}
.CodeRay .label{color:#970}
.CodeRay .local-variable{color:#963}
.CodeRay .octal{color:#40e}
.CodeRay .predefined{color:#369}
.CodeRay .preprocessor{color:#579}
.CodeRay .pseudo-class{color:#555}
.CodeRay .directive{font-weight:bold}
.CodeRay .type{font-weight:bold}
.CodeRay .predefined-type{color:inherit}
.CodeRay .reserved,.CodeRay .keyword {color:#000;font-weight:bold}
.CodeRay .key{color:#808}
.CodeRay .key .delimiter{color:#606}
.CodeRay .key .char{color:#80f}
.CodeRay .value{color:#088}
.CodeRay .regexp .delimiter{color:#808}
.CodeRay .regexp .content{color:#808}
.CodeRay .regexp .modifier{color:#808}
.CodeRay .regexp .char{color:#d14}
.CodeRay .regexp .function{color:#404;font-weight:bold}
.CodeRay .string{color:#d20}
.CodeRay .string .string .string{background:#ffd0d0}
.CodeRay .string .content{color:#d14}
.CodeRay .string .char{color:#d14}
.CodeRay .string .delimiter{color:#d14}
.CodeRay .shell{color:#d14}
.CodeRay .shell .delimiter{color:#d14}
.CodeRay .symbol{color:#990073}
.CodeRay .symbol .content{color:#a60}
.CodeRay .symbol .delimiter{color:#630}
.CodeRay .tag{color:#008080}
.CodeRay .tag-special{color:#d70}
.CodeRay .variable{color:#036}
.CodeRay .insert{background:#afa}
.CodeRay .delete{background:#faa}
.CodeRay .change{color:#aaf;background:#007}
.CodeRay .head{color:#f8f;background:#505}
.CodeRay .insert .insert{color:#080}
.CodeRay .delete .delete{color:#800}
.CodeRay .change .change{color:#66f}
.CodeRay .head .head{color:#f4f}
</style>
<link rel="stylesheet" href="../katex/katex.min.css">
<script src="../katex/katex.min.js"></script>
<script src="../katex/contrib/auto-render.min.js"></script>
<!-- Use KaTeX to render math once document is loaded, see
https://github.com/Khan/KaTeX/tree/master/contrib/auto-render -->
<script>
document.addEventListener("DOMContentLoaded", function () {
renderMathInElement(
document.body,
{
delimiters: [
{ left: "$$", right: "$$", display: true},
{ left: "\\[", right: "\\]", display: true},
{ left: "$", right: "$", display: false},
{ left: "\\(", right: "\\)", display: false}
]
}
);
});
</script></head>
<body class="book toc2 toc-left" style="max-width: 100;">
<div id="header">
<h1>The OpenCL<sup>&#8482;</sup> SPIR-V Environment Specification</h1>
<div class="details">
<span id="author" class="author">Khronos<sup>&#174;</sup> OpenCL Working Group</span><br>
<span id="revnumber">version v3.0.1-Provisional,</span>
<span id="revdate">Mon, 27 Apr 2020 04:09:40 +0000</span>
<br><span id="revremark">from git branch: master commit: fafc202e2b6a80bd2276596227317696d76e1f63</span>
</div>
<div id="toc" class="toc2">
<div id="toctitle">Table of Contents</div>
<ul class="sectlevel1">
<li><a href="#introduction">1. Introduction</a></li>
<li><a href="#common-properties">2. Common Properties</a>
<ul class="sectlevel2">
<li><a href="#_supported_spir_v_versions">2.1. Supported SPIR-V Versions</a></li>
<li><a href="#_extended_instruction_sets">2.2. Extended Instruction Sets</a></li>
<li><a href="#_source_language_encoding">2.3. Source Language Encoding</a></li>
<li><a href="#_numerical_type_formats">2.4. Numerical Type Formats</a></li>
<li><a href="#_supported_types">2.5. Supported Types</a></li>
<li><a href="#_image_channel_order_mapping">2.6. Image Channel Order Mapping</a></li>
<li><a href="#_image_channel_data_type_mapping">2.7. Image Channel Data Type Mapping</a></li>
<li><a href="#_kernels">2.8. Kernels</a></li>
</ul>
</li>
<li><a href="#required-capabilities">3. Required Capabilities</a>
<ul class="sectlevel2">
<li><a href="#required-capabilities-1.0">3.1. SPIR-V 1.0</a></li>
<li><a href="#required-capabilities-1.1">3.2. SPIR-V 1.1</a></li>
<li><a href="#required-capabilities-1.2">3.3. SPIR-V 1.2</a></li>
</ul>
</li>
<li><a href="#validation-rules">4. Validation Rules</a></li>
<li><a href="#opencl_extensions">5. OpenCL Extensions</a>
<ul class="sectlevel2">
<li><a href="#_declaring_spir_v_extensions">5.1. Declaring SPIR-V Extensions</a></li>
<li><a href="#_full_and_embedded_profile_extensions">5.2. Full and Embedded Profile Extensions</a></li>
<li><a href="#_embedded_profile_extensions">5.3. Embedded Profile Extensions</a></li>
</ul>
</li>
<li><a href="#numerical_compliance">6. OpenCL Numerical Compliance</a>
<ul class="sectlevel2">
<li><a href="#_rounding_modes">6.1. Rounding Modes</a></li>
<li><a href="#_rounding_modes_for_conversions">6.2. Rounding Modes for Conversions</a></li>
<li><a href="#_out_of_range_conversions">6.3. Out-of-Range Conversions</a></li>
<li><a href="#_inf_nan_and_denormalized_numbers">6.4. INF, NaN, and Denormalized Numbers</a></li>
<li><a href="#_floating_point_exceptions">6.5. Floating-Point Exceptions</a></li>
<li><a href="#relative-error-as-ulps">6.6. Relative Error as ULPs</a></li>
<li><a href="#_edge_case_behavior">6.7. Edge Case Behavior</a></li>
</ul>
</li>
<li><a href="#image_addressing_and_filtering">7. Image Addressing and Filtering</a>
<ul class="sectlevel2">
<li><a href="#image-coordinates">7.1. Image Coordinates</a></li>
<li><a href="#addressing-and-filter-modes">7.2. Addressing and Filter Modes</a></li>
<li><a href="#precision-of-addressing-and-filter-modes">7.3. Precision of Addressing and Filter Modes</a></li>
<li><a href="#conversion-rules">7.4. Conversion Rules</a></li>
<li><a href="#selecting-an-image-from-an-image-array">7.5. Selecting an Image from an Image Array</a></li>
<li><a href="#_data_format_for_reading_and_writing_images">7.6. Data Format for Reading and Writing Images</a></li>
<li><a href="#_sampled_and_sampler_less_reads">7.7. Sampled and Sampler-less Reads</a></li>
</ul>
</li>
<li><a href="#references">8. Normative References</a></li>
</ul>
</div>
</div>
<div id="content">
<div id="preamble">
<div class="sectionbody">
<div class="paragraph">
<p>Copyright 2008-2020 The Khronos Group.</p>
</div>
<div class="paragraph">
<p>This specification is protected by copyright laws and contains material proprietary
to the Khronos Group, Inc. Except as described by these terms, it or any components
may not be reproduced, republished, distributed, transmitted, displayed, broadcast
or otherwise exploited in any manner without the express prior written permission
of Khronos Group.</p>
</div>
<div class="paragraph">
<p>Khronos Group grants a conditional copyright license to use and reproduce the
unmodified specification for any purpose, without fee or royalty, EXCEPT no licenses
to any patent, trademark or other intellectual property rights are granted under
these terms. Parties desiring to implement the specification and make use of
Khronos trademarks in relation to that implementation, and receive reciprocal patent
license protection under the Khronos IP Policy must become Adopters and confirm the
implementation as conformant under the process defined by Khronos for this
specification; see <a href="https://www.khronos.org/adopters" class="bare">https://www.khronos.org/adopters</a>.</p>
</div>
<div class="paragraph">
<p>Khronos Group makes no, and expressly disclaims any, representations or warranties,
express or implied, regarding this specification, including, without limitation:
merchantability, fitness for a particular purpose, non-infringement of any
intellectual property, correctness, accuracy, completeness, timeliness, and
reliability. Under no circumstances will the Khronos Group, or any of its Promoters,
Contributors or Members, or their respective partners, officers, directors,
employees, agents or representatives be liable for any damages, whether direct,
indirect, special or consequential damages for lost revenues, lost profits, or
otherwise, arising from or in connection with these materials.</p>
</div>
<div class="paragraph">
<p>Vulkan and Khronos are registered trademarks, and OpenXR, SPIR, SPIR-V, SYCL, WebGL,
WebCL, OpenVX, OpenVG, EGL, COLLADA, glTF, NNEF, OpenKODE, OpenKCAM, StreamInput,
OpenWF, OpenSL ES, OpenMAX, OpenMAX AL, OpenMAX IL, OpenMAX DL, OpenML and DevU are
trademarks of the Khronos Group Inc. ASTC is a trademark of ARM Holdings PLC,
OpenCL is a trademark of Apple Inc. and OpenGL and OpenML are registered trademarks
and the OpenGL ES and OpenGL SC logos are trademarks of Silicon Graphics
International used under license by Khronos. All other product names, trademarks,
and/or company names are used solely for identification and belong to their
respective owners.</p>
</div>
<div style="page-break-after: always;"></div>
</div>
</div>
<div class="sect1">
<h2 id="introduction">1. Introduction</h2>
<div class="sectionbody">
<div class="paragraph">
<p><a href="#opencl-spec">OpenCL</a> is an open, royalty-free, standard for general
purpose parallel programming across CPUs, GPUs, and other processors, giving
software developers portable and efficient access to the power of
heterogeneous processing platforms.</p>
</div>
<div class="paragraph">
<p><a href="#spirv-spec">SPIR-V</a> is an open, royalty-free, standard intermediate
language capable of representing parallel compute kernels that are executed
by implementations of the OpenCL standard.</p>
</div>
<div class="paragraph">
<p>SPIR-V is adaptable to multiple execution environments: a SPIR-V module is
consumed by an execution environment, as specified by a client API.
This document describes the SPIR-V execution environment for implementations
of the OpenCL standard.
The SPIR-V execution environment describes required support for some SPIR-V
capabilities, additional semantics for some SPIR-V instructions, and
additional validation rules that a SPIR-V binary module must adhere to in
order to be considered valid.</p>
</div>
<div class="paragraph">
<p>This document is written for compiler developers who are generating SPIR-V
modules intended to be consumed by the OpenCL API, for implementors of the
OpenCL API who are consuming SPIR-V modules, and for software developers who
are using SPIR-V modules with the OpenCL API.</p>
</div>
<div class="admonitionblock note">
<table>
<tr>
<td class="icon">
<i class="fa icon-note" title="Note"></i>
</td>
<td class="content">
<div class="paragraph">
<p>The OpenCL 3.0 SPIR-V Environment described in this specification is provisional.
It has been Ratified under the Khronos Intellectual Property Framework, and is being made publicly available to enable review and feedback from the community.</p>
</div>
<div class="paragraph">
<p>If you have feedback please create an issue on <a href="https://github.com/KhronosGroup/OpenCL-Docs/" class="bare">https://github.com/KhronosGroup/OpenCL-Docs/</a></p>
</div>
</td>
</tr>
</table>
</div>
</div>
</div>
<div class="sect1">
<h2 id="common-properties">2. Common Properties</h2>
<div class="sectionbody">
<div class="paragraph">
<p>This section describes common properties of all OpenCL environments that
consume SPIR-V modules.</p>
</div>
<div class="paragraph">
<p>A SPIR-V module passed to an OpenCL environment is interpreted as a series
of 32-bit words in host endianness, with literal strings packed as described
in the SPIR-V specification.
The first few words of the SPIR-V module must be a magic number and a SPIR-V
version number, as described in the SPIR-V specification.</p>
</div>
<div class="sect2">
<h3 id="_supported_spir_v_versions">2.1. Supported SPIR-V Versions</h3>
<div class="paragraph">
<p>An OpenCL environment describes the versions of SPIR-V modules that it
supports using the <code>CL_&#8203;DEVICE_&#8203;IL_&#8203;VERSION</code> query in OpenCL 2.1 or newer,
the <code>CL_&#8203;DEVICE_&#8203;ILS_&#8203;WITH_&#8203;VERSION</code> query in OpenCL 3.0 or newer, or the
<code>CL_&#8203;DEVICE_&#8203;IL_&#8203;VERSION_&#8203;KHR</code> query in the <code>cl_khr_il_program</code> extension.</p>
</div>
<div class="paragraph">
<p>OpenCL environments that support the <code>cl_khr_il_program</code> extension or
OpenCL 2.1 must support SPIR-V 1.0 modules. OpenCL environments that support
OpenCL 2.2 must support SPIR-V 1.0, 1.1, and 1.2 modules.
Use the <code>CL_&#8203;DEVICE_&#8203;IL_&#8203;VERSION</code> or <code>CL_&#8203;DEVICE_&#8203;ILS_&#8203;WITH_&#8203;VERSION</code> query
to determine the versions of SPIR-V modules that are supported by
OpenCL environments that support OpenCL 3.0.</p>
</div>
</div>
<div class="sect2">
<h3 id="_extended_instruction_sets">2.2. Extended Instruction Sets</h3>
<div class="paragraph">
<p>OpenCL environments supporting SPIR-V must support SPIR-V modules that import
the <strong>OpenCL.std</strong>
<a href="#opencl-extended-instruction-set">extended instruction set for OpenCL</a>
using <strong>OpExtInstImport</strong>. For example:</p>
</div>
<div class="listingblock">
<div class="content">
<pre>... = OpExtInstImport "OpenCL.std"</pre>
</div>
</div>
</div>
<div class="sect2">
<h3 id="_source_language_encoding">2.3. Source Language Encoding</h3>
<div class="paragraph">
<p>If a SPIR-V module represents a program written in OpenCL C, then the
<em>Source Language</em> operand for the <strong>OpSource</strong> instruction should be
<strong>OpenCL_C</strong>, and the 32-bit literal language <em>Version</em> should describe the
version of OpenCL C, encoded MSB to LSB as:</p>
</div>
<div class="literalblock">
<div class="content">
<pre>0 | Major Number | Minor Number | Revision Number (optional)</pre>
</div>
</div>
<div class="paragraph">
<p>If a SPIR-V module represents a program written in OpenCL C++, then the
<em>Source Language</em> operand for the <strong>OpSource</strong> instruction should be
<strong>OpenCL_CPP</strong>, and the 32-bit literal language <em>Version</em> should describe the
version of OpenCL C++, encoded similarly.</p>
</div>
<div class="paragraph">
<p>The source language version is purely informational and has no semantic
meaning.</p>
</div>
</div>
<div class="sect2">
<h3 id="_numerical_type_formats">2.4. Numerical Type Formats</h3>
<div class="paragraph">
<p>For all OpenCL environments, floating-point types are represented and stored
using <a href="#ieee-754-spec">IEEE-754</a> semantics.
All integer formats are represented and stored using 2&#8217;s-complement format.</p>
</div>
</div>
<div class="sect2">
<h3 id="_supported_types">2.5. Supported Types</h3>
<div class="paragraph">
<p>The following types are supported by OpenCL environments.
Note that some types may require additional capabilities, and may not be
supported by all OpenCL environments.</p>
</div>
<div class="paragraph">
<p>OpenCL environments support arrays declared using <strong>OpTypeArray</strong>, structs
declared using <strong>OpTypeStruct</strong>, functions declared using <strong>OpTypeFunction</strong>,
and pointers declared using <strong>OpTypePointer</strong>.</p>
</div>
<div class="sect3">
<h4 id="_basic_scalar_and_vector_types">2.5.1. Basic Scalar and Vector Types</h4>
<div class="paragraph">
<p><strong>OpTypeVoid</strong> is supported.</p>
</div>
<div class="paragraph">
<p>The following scalar types are supported by OpenCL environments:</p>
</div>
<div class="ulist">
<ul>
<li>
<p><strong>OpTypeBool</strong></p>
</li>
<li>
<p><strong>OpTypeInt</strong>, with <em>Width</em> equal to 8, 16, 32, or 64, and with
<em>Signedness</em> equal to zero, indicating no signedness semantics.</p>
</li>
<li>
<p><strong>OpTypeFloat</strong>, with <em>Width</em> equal to 16, 32, or 64.</p>
</li>
</ul>
</div>
<div class="paragraph">
<p>OpenCL environments support vector types declared using <strong>OpTypeVector</strong>.
The vector <em>Component Type</em> may be any of the scalar types described
above.
Supported vector <em>Component Counts</em> are 2, 3, 4, 8, or 16.</p>
</div>
</div>
<div class="sect3">
<h4 id="_image_related_data_types">2.5.2. Image-Related Data Types</h4>
<div class="paragraph">
<p>The following table describes the <strong>OpTypeImage</strong> image types supported by
OpenCL environments:</p>
</div>
<table class="tableblock frame-all grid-all stretch">
<caption class="title">Table 1. Image Types</caption>
<colgroup>
<col style="width: 16.6666%;">
<col style="width: 16.6666%;">
<col style="width: 16.6666%;">
<col style="width: 50.0002%;">
</colgroup>
<thead>
<tr>
<th class="tableblock halign-left valign-top"><em>Dim</em></th>
<th class="tableblock halign-left valign-top"><em>Depth</em></th>
<th class="tableblock halign-left valign-top"><em>Arrayed</em></th>
<th class="tableblock halign-left valign-top"><strong>Description</strong></th>
</tr>
</thead>
<tbody>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>1D</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>0</code></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>0</code></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">A 1D image.</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>1D</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>0</code></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>1</code></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">A 1D image array.</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>2D</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>0</code></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>0</code></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">A 2D image.</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>2D</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>1</code></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>0</code></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">A 2D depth image.</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>2D</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>0</code></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>1</code></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">A 2D image array.</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>2D</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>1</code></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>1</code></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">A 2D depth image array.</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>3D</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>0</code></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>0</code></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">A 3D image.</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>Buffer</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>0</code></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>0</code></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">A 1D buffer image.</p></td>
</tr>
</tbody>
</table>
<div class="paragraph">
<p><strong>OpTypeSampler</strong> may be used to declare sampler types in OpenCL environments.</p>
</div>
</div>
<div class="sect3">
<h4 id="_other_data_types">2.5.3. Other Data Types</h4>
<div class="paragraph">
<p>The following table describes other data types that may be used in an
OpenCL environment:</p>
</div>
<table class="tableblock frame-all grid-all stretch">
<caption class="title">Table 2. Other Data Types</caption>
<colgroup>
<col style="width: 50%;">
<col style="width: 50%;">
</colgroup>
<thead>
<tr>
<th class="tableblock halign-left valign-top"><strong>Type</strong></th>
<th class="tableblock halign-left valign-top"><strong>Description</strong></th>
</tr>
</thead>
<tbody>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpTypeEvent</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">OpenCL event representing async copies from global to local memory and vice-versa.</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpTypeDeviceEvent</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">OpenCL device-side event representing commands enqueued to device command queues.</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpTypePipe</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">OpenCL pipe.</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpTypeReserveId</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">OpenCL pipe reservation identifier.</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpTypeQueue</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">OpenCL device-side command queue.</p></td>
</tr>
</tbody>
</table>
</div>
</div>
<div class="sect2">
<h3 id="_image_channel_order_mapping">2.6. Image Channel Order Mapping</h3>
<div class="paragraph">
<p>The following table describes how the results of the SPIR-V
<strong>OpImageQueryOrder</strong> instruction correspond to the OpenCL host API image
channel orders.</p>
</div>
<table class="tableblock frame-all grid-all stretch">
<caption class="title">Table 3. Image Channel Order mapping</caption>
<colgroup>
<col style="width: 50%;">
<col style="width: 50%;">
</colgroup>
<thead>
<tr>
<th class="tableblock halign-left valign-top"><strong>SPIR-V Image Channel Order</strong></th>
<th class="tableblock halign-left valign-top"><strong>OpenCL Image Channel Order</strong></th>
</tr>
</thead>
<tbody>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>R</code></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>CL_R</code></p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>A</code></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>CL_A</code></p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>RG</code></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>CL_RG</code></p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>RA</code></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>CL_RA</code></p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>RGB</code></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>CL_RGB</code></p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>RGBA</code></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>CL_RGBA</code></p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>BGRA</code></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>CL_BGRA</code></p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>ARGB</code></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>CL_ARGB</code></p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>Intensity</code></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>CL_INTENSITY</code></p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>Luminance</code></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>CL_LUMINANCE</code></p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>Rx</code></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>CL_Rx</code></p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>RGx</code></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>CL_RGx</code></p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>RGBx</code></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>CL_RGBx</code></p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>Depth</code></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>CL_DEPTH</code></p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>DepthStencil</code></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>CL_DEPTH_STENCIL</code></p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>sRGB</code></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>CL_sRGB</code></p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>sRGBA</code></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>CL_sRGBA</code></p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>sBGRA</code></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>CL_sBGRA</code></p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>sRGBx</code></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>CL_sRGBx</code></p></td>
</tr>
</tbody>
</table>
</div>
<div class="sect2">
<h3 id="_image_channel_data_type_mapping">2.7. Image Channel Data Type Mapping</h3>
<div class="paragraph">
<p>The following table describes how the results of the SPIR-V
<strong>OpImageQueryFormat</strong> instruction correspond to the OpenCL host API image
channel data types.</p>
</div>
<table class="tableblock frame-all grid-all stretch">
<caption class="title">Table 4. Image Channel Data Type mapping</caption>
<colgroup>
<col style="width: 50%;">
<col style="width: 50%;">
</colgroup>
<thead>
<tr>
<th class="tableblock halign-left valign-top"><strong>SPIR-V Image Channel Data Type</strong></th>
<th class="tableblock halign-left valign-top"><strong>OpenCL Image Channel Data Type</strong></th>
</tr>
</thead>
<tbody>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>SnormInt8</code></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>CL_SNORM_INT8</code></p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>SnormInt16</code></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>CL_SNORM_INT16</code></p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>UnormInt8</code></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>CL_UNORM_INT8</code></p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>UnormInt16</code></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>CL_UNORM_INT16</code></p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>UnormInt24</code></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>CL_UNORM_INT24</code></p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>UnormShort565</code></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>CL_UNORM_SHORT_565</code></p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>UnormShort555</code></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>CL_UNORM_SHORT_555</code></p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>UnormInt101010</code></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>CL_UNORM_INT_101010</code></p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>SignedInt8</code></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>CL_SIGNED_INT8</code></p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>SignedInt16</code></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>CL_SIGNED_INT16</code></p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>SignedInt32</code></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>CL_SIGNED_INT32</code></p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>UnsignedInt8</code></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>CL_UNSIGNED_INT8</code></p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>UnsignedInt16</code></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>CL_UNSIGNED_INT16</code></p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>UnsignedInt32</code></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>CL_UNSIGNED_INT32</code></p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>HalfFloat</code></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>CL_HALF_FLOAT</code></p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>Float</code></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>CL_FLOAT</code></p></td>
</tr>
</tbody>
</table>
</div>
<div class="sect2">
<h3 id="_kernels">2.8. Kernels</h3>
<div class="paragraph">
<p>An <strong>OpFunction</strong> in a SPIR-V module that is identified with <strong>OpEntryPoint</strong>
defines an OpenCL kernel that may be invoked using the OpenCL host API
enqueue kernel interfaces.</p>
</div>
<div class="sect3">
<h4 id="_kernel_return_types">2.8.1. Kernel Return Types</h4>
<div class="paragraph">
<p>The <em>Result Type</em> for an <strong>OpFunction</strong> identified with <strong>OpEntryPoint</strong> must be
<strong>OpTypeVoid</strong>.</p>
</div>
</div>
<div class="sect3">
<h4 id="_kernel_arguments">2.8.2. Kernel Arguments</h4>
<div class="paragraph">
<p>An <strong>OpFunctionParameter</strong> for an <strong>OpFunction</strong> that is identified with
<strong>OpEntryPoint</strong> defines an OpenCL kernel argument.
Allowed types for OpenCL kernel arguments are:</p>
</div>
<div class="ulist">
<ul>
<li>
<p><strong>OpTypeInt</strong></p>
</li>
<li>
<p><strong>OpTypeFloat</strong></p>
</li>
<li>
<p><strong>OpTypeStruct</strong></p>
</li>
<li>
<p><strong>OpTypeVector</strong></p>
</li>
<li>
<p><strong>OpTypePointer</strong></p>
</li>
<li>
<p><strong>OpTypeSampler</strong></p>
</li>
<li>
<p><strong>OpTypeImage</strong></p>
</li>
<li>
<p><strong>OpTypePipe</strong></p>
</li>
<li>
<p><strong>OpTypeQueue</strong></p>
</li>
</ul>
</div>
<div class="paragraph">
<p>For <strong>OpTypeInt</strong> parameters, supported <em>Widths</em> are 8, 16, 32, and 64, and
must have no signedness semantics.</p>
</div>
<div class="paragraph">
<p>For <strong>OpTypeFloat</strong> parameters, <em>Width</em> must be 32.</p>
</div>
<div class="paragraph">
<p>For <strong>OpTypeStruct</strong> parameters, supported structure <em>Member Types</em> are:</p>
</div>
<div class="ulist">
<ul>
<li>
<p><strong>OpTypeInt</strong></p>
</li>
<li>
<p><strong>OpTypeFloat</strong></p>
</li>
<li>
<p><strong>OpTypeStruct</strong></p>
</li>
<li>
<p><strong>OpTypeVector</strong></p>
</li>
<li>
<p><strong>OpTypePointer</strong></p>
</li>
</ul>
</div>
<div class="paragraph">
<p>For <strong>OpTypePointer</strong> parameters, supported <em>Storage Classes</em> are:</p>
</div>
<div class="ulist">
<ul>
<li>
<p><strong>CrossWorkgroup</strong></p>
</li>
<li>
<p><strong>Workgroup</strong></p>
</li>
<li>
<p><strong>UniformConstant</strong></p>
</li>
</ul>
</div>
<div class="paragraph">
<p>OpenCL kernel argument types must have a representation in the OpenCL host
API.</p>
</div>
<div class="paragraph">
<p>Environments that support extensions or optional features may allow
additional types in an entry point&#8217;s parameter list.</p>
</div>
</div>
</div>
</div>
</div>
<div class="sect1">
<h2 id="required-capabilities">3. Required Capabilities</h2>
<div class="sectionbody">
<div class="sect2">
<h3 id="required-capabilities-1.0">3.1. SPIR-V 1.0</h3>
<div class="paragraph">
<p>An OpenCL environment that supports SPIR-V 1.0 must support SPIR-V 1.0
modules that declare the following capabilities:</p>
</div>
<div class="ulist">
<ul>
<li>
<p><strong>Addresses</strong></p>
</li>
<li>
<p><strong>Float16Buffer</strong></p>
</li>
<li>
<p><strong>Int64</strong></p>
<div class="ulist">
<ul>
<li>
<p>For Full Profile devices.</p>
</li>
</ul>
</div>
</li>
<li>
<p><strong>Int16</strong></p>
</li>
<li>
<p><strong>Int8</strong></p>
</li>
<li>
<p><strong>Kernel</strong></p>
</li>
<li>
<p><strong>Linkage</strong></p>
</li>
<li>
<p><strong>Vector16</strong></p>
</li>
<li>
<p><strong>DeviceEnqueue</strong></p>
<div class="ulist">
<ul>
<li>
<p>For OpenCL 2.0, OpenCL 2.1, OpenCL 2.2, or OpenCL 3.0 devices supporting Device-Side Enqueue (where <code>CL_&#8203;DEVICE_&#8203;DEVICE_&#8203;ENQUEUE_&#8203;SUPPORT</code> is <code>CL_&#8203;TRUE</code>).</p>
</li>
</ul>
</div>
</li>
<li>
<p><strong>GenericPointer</strong></p>
<div class="ulist">
<ul>
<li>
<p>For OpenCL 2.0, OpenCL 2.1, OpenCL 2.2, or OpenCL 3.0 devices supporting the Generic Address Space (where <code>CL_&#8203;DEVICE_&#8203;GENERIC_&#8203;ADDRESS_&#8203;SPACE_&#8203;SUPPORT</code> is <code>CL_&#8203;TRUE</code>).</p>
</li>
</ul>
</div>
</li>
<li>
<p><strong>Groups</strong></p>
<div class="ulist">
<ul>
<li>
<p>For OpenCL 2.0, OpenCL 2.1, OpenCL 2.2, or OpenCL 3.0 devices supporting Subgroups (where <code>CL_&#8203;DEVICE_&#8203;MAX_&#8203;NUM_&#8203;SUB_&#8203;GROUPS</code> is not <code>0</code>) or Work Group Collective Functions (where <code>CL_&#8203;DEVICE_&#8203;WORK_&#8203;GROUP_&#8203;COLLECTIVE_&#8203;FUNCTIONS_&#8203;SUPPORT</code> is <code>CL_&#8203;TRUE</code>).</p>
</li>
</ul>
</div>
</li>
<li>
<p><strong>Pipes</strong></p>
<div class="ulist">
<ul>
<li>
<p>For OpenCL 2.0, OpenCL 2.1, OpenCL 2.2, or OpenCL 3.0 devices supporting Pipes (where <code>CL_&#8203;DEVICE_&#8203;PIPE_&#8203;SUPPORT</code> is <code>CL_&#8203;TRUE</code>).</p>
</li>
</ul>
</div>
</li>
<li>
<p><strong>ImageBasic</strong></p>
<div class="ulist">
<ul>
<li>
<p>For devices supporting Images (where <code>CL_&#8203;DEVICE_&#8203;IMAGE_&#8203;SUPPORT</code> is <code>CL_&#8203;TRUE</code>)</p>
</li>
</ul>
</div>
</li>
<li>
<p><strong>Float64</strong></p>
<div class="ulist">
<ul>
<li>
<p>For devices supporting Double Precision Floating-Point (where <code>CL_&#8203;DEVICE_&#8203;DOUBLE_&#8203;FP_&#8203;CONFIG</code> is not <code>0</code>)</p>
</li>
</ul>
</div>
</li>
</ul>
</div>
<div class="paragraph">
<p>If the OpenCL environment supports the <strong>ImageBasic</strong> capability, then
the following capabilities must also be supported:</p>
</div>
<div class="ulist">
<ul>
<li>
<p><strong>LiteralSampler</strong></p>
</li>
<li>
<p><strong>Sampled1D</strong></p>
</li>
<li>
<p><strong>Image1D</strong></p>
</li>
<li>
<p><strong>SampledBuffer</strong></p>
</li>
<li>
<p><strong>ImageBuffer</strong></p>
</li>
<li>
<p><strong>ImageReadWrite</strong></p>
<div class="ulist">
<ul>
<li>
<p>For OpenCL 2.0, OpenCL 2.1, OpenCL 2.2, or OpenCL 3.0 devices supporting Read-Write Images (where <code>CL_&#8203;DEVICE_&#8203;MAX_&#8203;READ_&#8203;WRITE_&#8203;IMAGE_&#8203;ARGS</code> is not <code>0</code>)</p>
</li>
</ul>
</div>
</li>
</ul>
</div>
</div>
<div class="sect2">
<h3 id="required-capabilities-1.1">3.2. SPIR-V 1.1</h3>
<div class="paragraph">
<p>An OpenCL environment supporting SPIR-V 1.1 must support SPIR-V 1.1
modules that declare the capabilities required for SPIR-V 1.0 modules,
above.</p>
</div>
<div class="paragraph">
<p>In addition, an OpenCL environment consuming SPIR-V 1.1 must support
SPIR-V 1.1 modules that declare the following capabilities:</p>
</div>
<div class="ulist">
<ul>
<li>
<p><strong>SubgroupDispatch</strong></p>
<div class="ulist">
<ul>
<li>
<p>For OpenCL 2.2 devices, or OpenCL 3.0 devices supporting Subgroups (where <code>CL_&#8203;DEVICE_&#8203;MAX_&#8203;NUM_&#8203;SUB_&#8203;GROUPS</code> is not <code>0</code>)</p>
</li>
</ul>
</div>
</li>
<li>
<p><strong>PipeStorage</strong></p>
<div class="ulist">
<ul>
<li>
<p>For OpenCL 2.2 devices.</p>
</li>
</ul>
</div>
</li>
</ul>
</div>
</div>
<div class="sect2">
<h3 id="required-capabilities-1.2">3.3. SPIR-V 1.2</h3>
<div class="paragraph">
<p>An OpenCL environment supporting SPIR-V 1.2 must support SPIR-V 1.2
modules that declare the capabilities required for SPIR-V 1.1 modules,
above.</p>
</div>
<div class="paragraph">
<p>SPIR-V 1.2 does not add any new required capabilities.</p>
</div>
</div>
</div>
</div>
<div class="sect1">
<h2 id="validation-rules">4. Validation Rules</h2>
<div class="sectionbody">
<div class="paragraph">
<p>The following are a list of validation rules that apply to SPIR-V modules
executing in all OpenCL environments:</p>
</div>
<div class="paragraph">
<p>The <em>Execution Model</em> declared in <strong>OpEntryPoint</strong> must be <strong>Kernel</strong>.</p>
</div>
<div class="paragraph">
<p>The <em>Addressing Model</em> declared in <strong>OpMemoryModel</strong> must be either:</p>
</div>
<div class="ulist">
<ul>
<li>
<p><strong>Physical32</strong> (for OpenCL devices reporting <code>32</code> for <code>CL_&#8203;DEVICE_&#8203;ADDRESS_&#8203;BITS</code>)</p>
</li>
<li>
<p><strong>Physical64</strong> (for OpenCL devices reporting <code>64</code> for <code>CL_&#8203;DEVICE_&#8203;ADDRESS_&#8203;BITS</code>)</p>
</li>
</ul>
</div>
<div class="paragraph">
<p>The <em>Memory Model</em> declared in <strong>OpMemoryModel</strong> must be <strong>OpenCL</strong>.</p>
</div>
<div class="paragraph">
<p>For all <strong>OpTypeInt</strong> integer type-declaration instructions:</p>
</div>
<div class="ulist">
<ul>
<li>
<p><em>Signedness</em> must be 0, indicating no signedness semantics.</p>
</li>
</ul>
</div>
<div class="paragraph">
<p>For all <strong>OpTypeImage</strong> type-declaration instructions:</p>
</div>
<div class="ulist">
<ul>
<li>
<p><em>Sampled Type</em> must be <strong>OpTypeVoid</strong>.</p>
</li>
<li>
<p><em>Sampled</em> must be 0, indicating that the image usage will be known at
run time, not at compile time.</p>
</li>
<li>
<p><em>MS</em> must be 0, indicating single-sampled content.</p>
</li>
<li>
<p><em>Arrayed</em> may only be set to 1, indicating arrayed content, when <em>Dim</em>
is set to <strong>1D</strong> or <strong>2D</strong>.</p>
</li>
<li>
<p><em>Image Format</em> must be <strong>Unknown</strong>, indicating that the image does not
have a specified format.</p>
</li>
<li>
<p>The optional image <em>Access Qualifier</em> must be present.</p>
</li>
</ul>
</div>
<div class="paragraph">
<p>The image write instruction <strong>OpImageWrite</strong> must not include any optional
<em>Image Operands</em>.</p>
</div>
<div class="paragraph">
<p>The image read instructions <strong>OpImageRead</strong> and <strong>OpImageSampleExplicitLod</strong>
must not include the optional <em>Image Operand</em> <strong>ConstOffset</strong>.</p>
</div>
<div class="paragraph">
<p>For all <strong>Atomic Instructions</strong>:</p>
</div>
<div class="ulist">
<ul>
<li>
<p>Only 32-bit integer types are supported for the <em>Result Type</em> and/or
type of <em>Value</em>.</p>
</li>
<li>
<p>The <em>Pointer</em> operand must be a pointer to the <strong>Function</strong>, <strong>Workgroup</strong>,
or <strong>CrossWorkGroup</strong> <em>Storage Classes</em>. Note that an <strong>Atomic Instruction</strong>
on a pointer to the <strong>Function</strong> <em>Storage Class</em> is valid, but does not
have defined behavior.</p>
</li>
</ul>
</div>
<div class="paragraph">
<p>Recursion is not supported.
The static function call graph for an entry point must not contain cycles.</p>
</div>
<div class="paragraph">
<p>Whether irreducible control flow is legal is implementation defined.</p>
</div>
<div class="paragraph">
<p>For the instructions <strong>OpGroupAsyncCopy</strong> and <strong>OpGroupWaitEvents</strong>,
<em>Scope</em> for <em>Execution</em> must be:</p>
</div>
<div class="ulist">
<ul>
<li>
<p><strong>Workgroup</strong></p>
</li>
</ul>
</div>
<div class="paragraph">
<p>For the <strong>Group and Subgroup Instructions</strong>, <em>Scope</em> for <em>Execution</em> must
be one of:</p>
</div>
<div class="ulist">
<ul>
<li>
<p><strong>Workgroup</strong></p>
<div class="ulist">
<ul>
<li>
<p>For OpenCL 2.0, OpenCL 2.1, OpenCL 2.2, or OpenCL 3.0 devices
supporting Work Group Collective Functions (where
<code>CL_&#8203;DEVICE_&#8203;WORK_&#8203;GROUP_&#8203;COLLECTIVE_&#8203;FUNCTIONS_&#8203;SUPPORT</code> is <code>CL_&#8203;TRUE</code>).</p>
</li>
</ul>
</div>
</li>
<li>
<p><strong>Subgroup</strong></p>
<div class="ulist">
<ul>
<li>
<p>For OpenCL 2.1, OpenCL 2.2, or OpenCL 3.0 devices supporting
Subgroups (where <code>CL_&#8203;DEVICE_&#8203;MAX_&#8203;NUM_&#8203;SUB_&#8203;GROUPS</code> is not <code>0</code>)</p>
</li>
</ul>
</div>
</li>
</ul>
</div>
<div class="paragraph">
<p>For all other instructions, <em>Scope</em> for <em>Execution</em> must be one of:</p>
</div>
<div class="ulist">
<ul>
<li>
<p><strong>Workgroup</strong></p>
</li>
<li>
<p><strong>Subgroup</strong></p>
<div class="ulist">
<ul>
<li>
<p>For OpenCL 2.1, OpenCL 2.2, or OpenCL 3.0 devices supporting
Subgroups (where <code>CL_&#8203;DEVICE_&#8203;MAX_&#8203;NUM_&#8203;SUB_&#8203;GROUPS</code> is not <code>0</code>)</p>
</li>
</ul>
</div>
</li>
</ul>
</div>
<div class="paragraph">
<p>In an OpenCL 1.2 environment,
for the <strong>Barrier Instructions</strong> <strong>OpControlBarrier</strong> and <strong>OpMemoryBarrier</strong>, the
<em>Scope</em> for <em>Memory</em> must be <strong>Workgroup</strong>, and the memory-order constraint in
<em>Memory Semantics</em> must be <strong>SequentiallyConsistent</strong>.
Otherwise, <em>Scope</em> for <em>Memory</em> must be one of:</p>
</div>
<div class="ulist">
<ul>
<li>
<p><strong>CrossDevice</strong></p>
<div class="ulist">
<ul>
<li>
<p>For OpenCL 2.0, OpenCL 2.1, OpenCL 2.2, or OpenCL 3.0 devices
supporting <code>CL_&#8203;DEVICE_&#8203;ATOMIC_&#8203;SCOPE_&#8203;ALL_&#8203;DEVICES</code> in
<code>CL_&#8203;DEVICE_&#8203;ATOMIC_&#8203;FENCE_&#8203;CAPABILITIES</code>.</p>
</li>
</ul>
</div>
</li>
<li>
<p><strong>Device</strong></p>
<div class="ulist">
<ul>
<li>
<p>For OpenCL 2.0, OpenCL 2.1, OpenCL 2.2, or OpenCL 3.0 devices
supporting <code>CL_&#8203;DEVICE_&#8203;ATOMIC_&#8203;SCOPE_&#8203;DEVICE</code> in
<code>CL_&#8203;DEVICE_&#8203;ATOMIC_&#8203;FENCE_&#8203;CAPABILITIES</code>.</p>
</li>
</ul>
</div>
</li>
<li>
<p><strong>Workgroup</strong></p>
<div class="ulist">
<ul>
<li>
<p>For OpenCL 2.0, OpenCL 2.1, OpenCL 2.2, or OpenCL 3.0 devices
supporting <code>CL_&#8203;DEVICE_&#8203;ATOMIC_&#8203;SCOPE_&#8203;WORK_&#8203;GROUP</code> in
<code>CL_&#8203;DEVICE_&#8203;ATOMIC_&#8203;FENCE_&#8203;CAPABILITIES</code>.</p>
</li>
</ul>
</div>
</li>
<li>
<p><strong>Subgroup</strong></p>
<div class="ulist">
<ul>
<li>
<p>For OpenCL 2.1, OpenCL 2.2, or OpenCL 3.0 devices supporting
Subgroups (where <code>CL_&#8203;DEVICE_&#8203;MAX_&#8203;NUM_&#8203;SUB_&#8203;GROUPS</code> is not <code>0</code>).</p>
</li>
</ul>
</div>
</li>
<li>
<p><strong>Invocation</strong></p>
<div class="ulist">
<ul>
<li>
<p>For OpenCL 2.0, OpenCL 2.1, OpenCL 2.2, or OpenCL 3.0 devices
supporting <code>CL_&#8203;DEVICE_&#8203;ATOMIC_&#8203;SCOPE_&#8203;WORK_&#8203;ITEM</code> in
<code>CL_&#8203;DEVICE_&#8203;ATOMIC_&#8203;FENCE_&#8203;CAPABILITIES</code>.</p>
</li>
</ul>
</div>
</li>
</ul>
</div>
<div class="paragraph">
<p>And, the memory-order constraint in <em>Memory Semantics</em> must be one of:</p>
</div>
<div class="ulist">
<ul>
<li>
<p><strong>None (Relaxed)</strong></p>
<div class="ulist">
<ul>
<li>
<p>For OpenCL 2.0, OpenCL 2.1, OpenCL 2.2, or OpenCL 3.0 devices
supporting <code>CL_&#8203;DEVICE_&#8203;ATOMIC_&#8203;ORDER_&#8203;RELAXED</code> in
<code>CL_&#8203;DEVICE_&#8203;ATOMIC_&#8203;FENCE_&#8203;CAPABILITIES</code>.</p>
</li>
</ul>
</div>
</li>
<li>
<p><strong>Acquire</strong>, <strong>Release</strong>, or <strong>AcquireRelease</strong></p>
<div class="ulist">
<ul>
<li>
<p>For OpenCL 2.0, OpenCL 2.1, OpenCL 2.2, or OpenCL 3.0 devices
supporting <code>CL_&#8203;DEVICE_&#8203;ATOMIC_&#8203;ORDER_&#8203;ACQ_&#8203;REL</code> in
<code>CL_&#8203;DEVICE_&#8203;ATOMIC_&#8203;FENCE_&#8203;CAPABILITIES</code>.</p>
</li>
</ul>
</div>
</li>
<li>
<p><strong>SequentiallyConsistent</strong></p>
<div class="ulist">
<ul>
<li>
<p>For OpenCL 2.0, OpenCL 2.1, OpenCL 2.2, or OpenCL 3.0 devices
supporting <code>CL_&#8203;DEVICE_&#8203;ATOMIC_&#8203;ORDER_&#8203;SEQ_&#8203;CST</code> in
<code>CL_&#8203;DEVICE_&#8203;ATOMIC_&#8203;FENCE_&#8203;CAPABILITIES</code>.</p>
</li>
</ul>
</div>
</li>
</ul>
</div>
<div class="paragraph">
<p>In an OpenCL 1.2 environment,
for the <strong>Atomic Instructions</strong>, the <em>Scope</em> for <em>Memory</em> must be <strong>Device</strong>,
and the memory-order constraint in <em>Memory Semantics</em> must be <strong>Relaxed</strong>.
Otherwise, <em>Scope</em> for <em>Memory</em> must be one of:</p>
</div>
<div class="ulist">
<ul>
<li>
<p><strong>CrossDevice</strong></p>
<div class="ulist">
<ul>
<li>
<p>For OpenCL 2.0, OpenCL 2.1, OpenCL 2.2, or OpenCL 3.0 devices
supporting <code>CL_&#8203;DEVICE_&#8203;ATOMIC_&#8203;SCOPE_&#8203;ALL_&#8203;DEVICES</code> in
<code>CL_&#8203;DEVICE_&#8203;ATOMIC_&#8203;MEMORY_&#8203;CAPABILITIES</code>.</p>
</li>
</ul>
</div>
</li>
<li>
<p><strong>Device</strong></p>
<div class="ulist">
<ul>
<li>
<p>For OpenCL 2.0, OpenCL 2.1, OpenCL 2.2, or OpenCL 3.0 devices
supporting <code>CL_&#8203;DEVICE_&#8203;ATOMIC_&#8203;SCOPE_&#8203;DEVICE</code> in
<code>CL_&#8203;DEVICE_&#8203;ATOMIC_&#8203;MEMORY_&#8203;CAPABILITIES</code>.</p>
</li>
</ul>
</div>
</li>
<li>
<p><strong>Workgroup</strong></p>
<div class="ulist">
<ul>
<li>
<p>For OpenCL 2.0, OpenCL 2.1, OpenCL 2.2, or OpenCL 3.0 devices
supporting <code>CL_&#8203;DEVICE_&#8203;ATOMIC_&#8203;SCOPE_&#8203;WORK_&#8203;GROUP</code> in
<code>CL_&#8203;DEVICE_&#8203;ATOMIC_&#8203;MEMORY_&#8203;CAPABILITIES</code>.</p>
</li>
</ul>
</div>
</li>
<li>
<p><strong>Subgroup</strong></p>
<div class="ulist">
<ul>
<li>
<p>For OpenCL 2.1, OpenCL 2.2, or OpenCL 3.0 devices supporting
Subgroups (where <code>CL_&#8203;DEVICE_&#8203;MAX_&#8203;NUM_&#8203;SUB_&#8203;GROUPS</code> is not <code>0</code>).</p>
</li>
</ul>
</div>
</li>
</ul>
</div>
<div class="paragraph">
<p>And, the memory-order constraint in <em>Memory Semantics</em> must be one of:</p>
</div>
<div class="ulist">
<ul>
<li>
<p><strong>None (Relaxed)</strong></p>
<div class="ulist">
<ul>
<li>
<p>For OpenCL 2.0, OpenCL 2.1, OpenCL 2.2, or OpenCL 3.0 devices
supporting <code>CL_&#8203;DEVICE_&#8203;ATOMIC_&#8203;ORDER_&#8203;RELAXED</code> in
<code>CL_&#8203;DEVICE_&#8203;ATOMIC_&#8203;MEMORY_&#8203;CAPABILITIES</code>.</p>
</li>
</ul>
</div>
</li>
<li>
<p><strong>Acquire</strong>, <strong>Release</strong>, or <strong>AcquireRelease</strong></p>
<div class="ulist">
<ul>
<li>
<p>For OpenCL 2.0, OpenCL 2.1, OpenCL 2.2, or OpenCL 3.0 devices
supporting <code>CL_&#8203;DEVICE_&#8203;ATOMIC_&#8203;ORDER_&#8203;ACQ_&#8203;REL</code> in
<code>CL_&#8203;DEVICE_&#8203;ATOMIC_&#8203;MEMORY_&#8203;CAPABILITIES</code>.</p>
</li>
</ul>
</div>
</li>
<li>
<p><strong>SequentiallyConsistent</strong></p>
<div class="ulist">
<ul>
<li>
<p>For OpenCL 2.0, OpenCL 2.1, OpenCL 2.2, or OpenCL 3.0 devices
supporting <code>CL_&#8203;DEVICE_&#8203;ATOMIC_&#8203;ORDER_&#8203;SEQ_&#8203;CST</code> in
<code>CL_&#8203;DEVICE_&#8203;ATOMIC_&#8203;MEMORY_&#8203;CAPABILITIES</code>.</p>
</li>
</ul>
</div>
</li>
</ul>
</div>
<div class="paragraph">
<p>For OpenCL environments that support and declare the <strong>GenericPointer</strong>
capability, the <em>Pointer</em> operand to all <strong>Atomic Instructions</strong> may be
a pointer to the <strong>Generic</strong> <em>Storage Class</em>, however behavior is still
undefined if the <strong>Generic</strong> pointer represents a pointer to the
<strong>Function</strong> <em>Storage Class</em>.</p>
</div>
</div>
</div>
<div class="sect1">
<h2 id="opencl_extensions">5. OpenCL Extensions</h2>
<div class="sectionbody">
<div class="paragraph">
<p>An OpenCL environment may be modified by <a href="#opencl-extension-spec">OpenCL
extensions</a>. For example, some OpenCL extensions may require support
for support for additional SPIR-V capabilities or instructions, or by
relaxing SPIR-V restrictions.
Some OpenCL extensions may modify the OpenCL environment by requiring
consumption of a SPIR-V module that uses a SPIR-V extension. In this case,
the implementation will include the OpenCL extension in the host API
<code>CL_PLATFORM_EXTENSIONS</code> or <code>CL_DEVICE_EXTENSIONS</code> string, but not the
corresponding SPIR-V extension.</p>
</div>
<div class="paragraph">
<p>This section describes how the OpenCL environment is modified by Khronos
(<code>khr</code>) OpenCL extensions. Other OpenCL extensions, such as multi-vendor
(<code>ext</code>) extensions or vendor-specific extensions, describe how they modify
the OpenCL environment in their individual extension specifications. The
Khronos OpenCL extensions require no corresponding SPIR-V extensions.</p>
</div>
<div class="sect2">
<h3 id="_declaring_spir_v_extensions">5.1. Declaring SPIR-V Extensions</h3>
<div class="paragraph">
<p>A SPIR-V module declares use of a SPIR-V extension using <strong>OpExtension</strong> and
the name of the SPIR-V extension. For example:</p>
</div>
<div class="listingblock">
<div class="content">
<pre>OpExtension "SPV_KHR_extension_name"</pre>
</div>
</div>
<div class="paragraph">
<p>Only use of SPIR-V extensions may be declared in a SPIR-V module using
<strong>OpExtension</strong>; there is never a need to declare use of an OpenCL extension
in a SPIR-V module using <strong>OpExtension</strong>.</p>
</div>
</div>
<div class="sect2">
<h3 id="_full_and_embedded_profile_extensions">5.2. Full and Embedded Profile Extensions</h3>
<div class="sect3">
<h4 id="_cl_khr_3d_image_writes">5.2.1. <code>cl_khr_3d_image_writes</code></h4>
<div class="paragraph">
<p>If the OpenCL environment supports the extension <code>cl_khr_3d_image_writes</code>,
then the environment must accept <em>Image</em> operands to <strong>OpImageWrite</strong> that
are declared with with dimensionality <em>Dim</em> equal to <strong>3D</strong>.</p>
</div>
</div>
<div class="sect3">
<h4 id="_cl_khr_depth_images">5.2.2. <code>cl_khr_depth_images</code></h4>
<div class="paragraph">
<p>If the OpenCL environment supports the extension <code>cl_khr_depth_images</code>,
then the environment must accept modules that declare 2D depth image types
using <strong>OpTypeImage</strong> with dimensionality <em>Dim</em> equal to <strong>2D</strong> and <em>Depth</em>
equal to 1, indicating a depth image. 2D depth images may optionally be
<em>Arrayed</em>, if supported.</p>
</div>
<div class="paragraph">
<p>Additionally, the following Image Channel Orders may be returned by
<strong>OpImageQueryOrder</strong>:</p>
</div>
<div class="ulist">
<ul>
<li>
<p><strong>Depth</strong></p>
</li>
</ul>
</div>
</div>
<div class="sect3">
<h4 id="_cl_khr_device_enqueue_local_arg_types">5.2.3. <code>cl_khr_device_enqueue_local_arg_types</code></h4>
<div class="paragraph">
<p>If the OpenCL environment supports the extension
<code>cl_khr_device_enqueue_local_arg_types</code>, then then environment will allow
<em>Invoke</em> functions to be passed to <strong>OpEnqueueKernel</strong> with <strong>Workgroup</strong>
memory pointer parameters of any type.</p>
</div>
</div>
<div class="sect3">
<h4 id="_cl_khr_fp16">5.2.4. <code>cl_khr_fp16</code></h4>
<div class="paragraph">
<p>If the OpenCL environment supports the extension <code>cl_khr_fp16</code>, then the
environment must accept modules that declare the following SPIR-V
capabilities:</p>
</div>
<div class="ulist">
<ul>
<li>
<p><strong>Float16</strong></p>
</li>
</ul>
</div>
</div>
<div class="sect3">
<h4 id="_cl_khr_fp64">5.2.5. <code>cl_khr_fp64</code></h4>
<div class="paragraph">
<p>If the OpenCL environment supports the extension <code>cl_khr_fp64</code>, then the
environment must accept modules that declare the following SPIR-V
capabilities:</p>
</div>
<div class="ulist">
<ul>
<li>
<p><strong>Float64</strong></p>
</li>
</ul>
</div>
</div>
<div class="sect3">
<h4 id="_cl_khr_gl_depth_images">5.2.6. <code>cl_khr_gl_depth_images</code></h4>
<div class="paragraph">
<p>If the OpenCL environment supports the extension <code>cl_khr_gl_depth_images</code>,
then the following Image Channel Orders may additionally be returned by
<strong>OpImageQueryOrder</strong>:</p>
</div>
<div class="ulist">
<ul>
<li>
<p><strong>DepthStencil</strong></p>
</li>
</ul>
</div>
<div class="paragraph">
<p>Also, the following Image Channel Data Types may additionally be returned by
<strong>OpImageQueryFormat</strong>:</p>
</div>
<div class="ulist">
<ul>
<li>
<p><strong>UnormInt24</strong></p>
</li>
</ul>
</div>
</div>
<div class="sect3">
<h4 id="_cl_khr_gl_msaa_sharing">5.2.7. <code>cl_khr_gl_msaa_sharing</code></h4>
<div class="paragraph">
<p>If the OpenCL environment supports the extension <code>cl_khr_gl_msaa_sharing</code>,
then the environment must accept modules that declare 2D multi-sampled
image types using <strong>OpTypeImage</strong> with dimensionality <em>Dim</em> equal to <strong>2D</strong> and
<em>MS</em> equal to 1, indicating multi-sampled content. 2D multi-sampled images
may optionally be <em>Arrayed</em> or <em>Depth</em> images, if supported.</p>
</div>
<div class="paragraph">
<p>The 2D multi-sampled images may be used with the following instructions:</p>
</div>
<div class="ulist">
<ul>
<li>
<p><strong>OpImageRead</strong></p>
</li>
<li>
<p><strong>OpImageQuerySizeLod</strong></p>
</li>
<li>
<p><strong>OpImageQueryFormat</strong></p>
</li>
<li>
<p><strong>OpImageQueryOrder</strong></p>
</li>
<li>
<p><strong>OpImageQuerySamples</strong></p>
</li>
</ul>
</div>
</div>
<div class="sect3">
<h4 id="_cl_khr_int64_base_atomics_and_cl_khr_int64_extended_atomics">5.2.8. <code>cl_khr_int64_base_atomics</code> and <code>cl_khr_int64_extended_atomics</code></h4>
<div class="paragraph">
<p>If the OpenCL environment supports the extension <code>cl_khr_int64_base_atomics</code>
or <code>cl_khr_int64_extended_atomics</code>, then the environment must accept modules
that declare the following SPIR-V capabilities:</p>
</div>
<div class="ulist">
<ul>
<li>
<p><strong>Int64Atomics</strong></p>
</li>
</ul>
</div>
<div class="paragraph">
<p>When the <strong>Int64Atomics</strong> capability is declared, 64-bit integer types are
valid for the <em>Result Type</em> and type of <em>Value</em> for all <strong>Atomic Instructions</strong>.</p>
</div>
<div class="paragraph">
<p>Note: OpenCL environments that consume SPIR-V must support both
<code>cl_khr_int64_base_atomics</code> and <code>cl_khr_int64_extended_atomics</code> or neither
of these extensions.</p>
</div>
</div>
<div class="sect3">
<h4 id="_cl_khr_mipmap_image">5.2.9. <code>cl_khr_mipmap_image</code></h4>
<div class="paragraph">
<p>If the OpenCL environment supports the extension <code>cl_khr_mipmap_image</code>,
then the environment must accept non-zero optional <strong>Lod</strong> <em>Image Operands</em>
for the following instructions:</p>
</div>
<div class="ulist">
<ul>
<li>
<p><strong>OpImageSampleExplicitLod</strong></p>
</li>
<li>
<p><strong>OpImageRead</strong></p>
</li>
<li>
<p><strong>OpImageQuerySizeLod</strong></p>
</li>
</ul>
</div>
<div class="paragraph">
<p>Note: Implementations that support <code>cl_khr_mipmap_image</code> are not guaranteed
to support the <strong>ImageMipmap</strong> capability, since this extension does not
require non-zero optional <strong>Lod</strong> <em>Image Operands</em> for <strong>OpImageWrite</strong>.</p>
</div>
</div>
<div class="sect3">
<h4 id="_cl_khr_mipmap_image_writes">5.2.10. <code>cl_khr_mipmap_image_writes</code></h4>
<div class="paragraph">
<p>If the OpenCL environment supports the extension <code>cl_khr_mipmap_image_writes</code>,
then the environment must accept non-zero optional <strong>Lod</strong> <em>Image Operands</em>
for the following instructions:</p>
</div>
<div class="ulist">
<ul>
<li>
<p><strong>OpImageWrite</strong></p>
</li>
</ul>
</div>
<div class="paragraph">
<p>Note: An implementation that supports <code>cl_khr_mipmap_image_writes</code> must also
support <code>cl_khr_mipmap_image</code>, and support for both extensions does
guarantee support for the <strong>ImageMipmap</strong> capability.</p>
</div>
</div>
<div class="sect3">
<h4 id="_cl_khr_subgroups">5.2.11. <code>cl_khr_subgroups</code></h4>
<div class="paragraph">
<p>If the OpenCL environment supports the extension <code>cl_khr_subgroups</code>, then
for all instructions except <strong>OpGroupAsyncCopy</strong> and <strong>OpGroupWaitEvents</strong>
the <em>Scope</em> for <em>Execution</em> may be:</p>
</div>
<div class="ulist">
<ul>
<li>
<p><strong>Subgroup</strong></p>
</li>
</ul>
</div>
<div class="paragraph">
<p>Additionally, for all instructions except <strong>Atomic Instructions</strong> in an
OpenCL 1.2 environment, the <em>Scope</em> for <em>Memory</em> may be:</p>
</div>
<div class="ulist">
<ul>
<li>
<p><strong>Subgroup</strong></p>
</li>
</ul>
</div>
</div>
<div class="sect3">
<h4 id="_cl_khr_subgroup_named_barrier">5.2.12. <code>cl_khr_subgroup_named_barrier</code></h4>
<div class="paragraph">
<p>If the OpenCL environment supports the extension
<code>cl_khr_subgroup_named_barrier</code>, then the environment must accept modules
that declare the following SPIR-V capabilities:</p>
</div>
<div class="ulist">
<ul>
<li>
<p><strong>NamedBarrier</strong></p>
</li>
</ul>
</div>
</div>
<div class="sect3">
<h4 id="_cl_khr_spirv_no_integer_wrap_decoration">5.2.13. <code>cl_khr_spirv_no_integer_wrap_decoration</code></h4>
<div class="paragraph">
<p>If the OpenCL environment supports the extension <code>cl_khr_spirv_no_integer_wrap_decoration</code>, then the environment must accept modules that declare use of the extension <code>SPV_KHR_no_integer_wrap_decoration</code> via <strong>OpExtension</strong>.</p>
</div>
<div class="paragraph">
<p>If the OpenCL environment supports the extension <code>cl_khr_spirv_no_integer_wrap_decoration</code> and use of the SPIR-V extension <code>SPV_KHR_no_integer_wrap_decoration</code> is declared in the module via <strong>OpExtension</strong>, then the environment must accept modules that include the <strong>NoSignedWrap</strong> or <strong>NoUnsignedWrap</strong> decorations.</p>
</div>
</div>
</div>
<div class="sect2">
<h3 id="_embedded_profile_extensions">5.3. Embedded Profile Extensions</h3>
<div class="sect3">
<h4 id="_cles_khr_int64">5.3.1. <code>cles_khr_int64</code></h4>
<div class="paragraph">
<p>If the OpenCL environment supports the extension <code>cles_khr_int64</code>, then the
environment must accept modules that declare the following SPIR-V
capabilities:</p>
</div>
<div class="ulist">
<ul>
<li>
<p><strong>Int64</strong></p>
</li>
</ul>
</div>
</div>
</div>
</div>
</div>
<div class="sect1">
<h2 id="numerical_compliance">6. OpenCL Numerical Compliance</h2>
<div class="sectionbody">
<div class="paragraph">
<p>This section describes features of the <a href="#cpp14-spec">C++14</a> and
<a href="#ieee-754-spec">IEEE-754</a> standards that must be supported by all OpenCL
compliant devices.</p>
</div>
<div class="paragraph">
<p>This section describes the functionality that must be supported by all
OpenCL devices for single precision floating-point numbers.
Currently, only single precision floating-point is a requirement.
Half precision floating-point is an optional feature indicated by the
<strong>Float16</strong> capability.
Double precision floating-point is also an optional feature indicated by the
<strong>Float64</strong> capability.</p>
</div>
<div class="sect2">
<h3 id="_rounding_modes">6.1. Rounding Modes</h3>
<div class="paragraph">
<p>Floating-point calculations may be carried out internally with extra
precision and then rounded to fit into the destination type.
IEEE 754 defines four possible rounding modes:</p>
</div>
<div class="ulist">
<ul>
<li>
<p><em>Round to nearest even</em></p>
</li>
<li>
<p><em>Round toward +infinity</em></p>
</li>
<li>
<p><em>Round toward -infinity</em></p>
</li>
<li>
<p><em>Round toward zero</em></p>
</li>
</ul>
</div>
<div class="paragraph">
<p>The complete set of rounding modes supported by the device are described by
the <code>CL_DEVICE_SINGLE_FP_CONFIG</code>, <code>CL_DEVICE_HALF_FP_CONFIG</code>, and
<code>CL_DEVICE_DOUBLE_FP_CONFIG</code> device queries.</p>
</div>
<div class="paragraph">
<p>For double precision operations, <em>Round to nearest even</em> is a required
rounding mode, and is therefore the default rounding mode for double
precision operations.</p>
</div>
<div class="paragraph">
<p>For single precision operations, devices supporting the full profile must
support <em>Round to nearest even</em>, therefore for full profile devices this is
the default rounding mode for single precision operations.
Devices supporting the embedded profile may support either <em>Round to nearest
even</em> or <em>Round toward zero</em> as the default rounding mode for single
precision operations.</p>
</div>
<div class="paragraph">
<p>For half precision operations, devices may support either <em>Round to nearest
even</em> or <em>Round toward zero</em> as the default rounding mode for half precision
operations.</p>
</div>
<div class="paragraph">
<p>Only static selection of rounding mode is supported.
Dynamically reconfiguring the rounding mode as specified by the IEEE 754
spec is not supported.</p>
</div>
</div>
<div class="sect2">
<h3 id="_rounding_modes_for_conversions">6.2. Rounding Modes for Conversions</h3>
<div class="paragraph">
<p>Results of the following conversion instructions may include an optional
<strong>FPRoundingMode</strong> decoration:</p>
</div>
<div class="ulist">
<ul>
<li>
<p><strong>OpConvertFToU</strong></p>
</li>
<li>
<p><strong>OpConvertFToS</strong></p>
</li>
<li>
<p><strong>OpConvertSToF</strong></p>
</li>
<li>
<p><strong>OpConvertUToF</strong></p>
</li>
<li>
<p><strong>OpFConvert</strong></p>
</li>
</ul>
</div>
<div class="paragraph">
<p>The <strong>FPRoundingMode</strong> decoration may not be added to results of any other
instruction.</p>
</div>
<div class="paragraph">
<p>If no rounding mode is specified explicitly via an <strong>FPRoundingMode</strong>
decoration, then the default rounding mode for conversion operations is:</p>
</div>
<div class="ulist">
<ul>
<li>
<p><em>Round to nearest even</em>, for conversions to floating-point types.</p>
</li>
<li>
<p><em>Round toward zero</em>, for conversions from floating-point to integer types.</p>
</li>
</ul>
</div>
</div>
<div class="sect2">
<h3 id="_out_of_range_conversions">6.3. Out-of-Range Conversions</h3>
<div class="paragraph">
<p>When a conversion operand is either greater than the greatest representable
destination value or less than the least representable destination value,
it is said to be out-of-range.</p>
</div>
<div class="paragraph">
<p>Converting an out-of-range integer to an integer type without a
<strong>SaturatedConversion</strong> decoration follows <a href="#C99-spec">C99</a>/<a href="#cpp14-spec">C++14</a> conversion rules.</p>
</div>
<div class="paragraph">
<p>Converting an out-of-range floating point number to an integer type without
a <strong>SaturatedConversion</strong> decoration is implementation-defined.</p>
</div>
</div>
<div class="sect2">
<h3 id="_inf_nan_and_denormalized_numbers">6.4. INF, NaN, and Denormalized Numbers</h3>
<div class="paragraph">
<p>INFs and NaNs must be supported.
Support for signaling NaNs is not required.</p>
</div>
<div class="paragraph">
<p>Support for denormalized numbers with single precision and half precision
floating-point is optional.
Denormalized single precision or half precision floating-point numbers
passed as the input or produced as the output of single precision or half
precision floating-point operations may be flushed to zero.
Support for denormalized numbers is required for double precision
floating-point.</p>
</div>
<div class="paragraph">
<p>Support for INFs, NaNs, and denormalized numbers is described by the
<code>CL_FP_DENORM</code> and <code>CL_FP_INF_NAN</code> bits in the <code>CL_DEVICE_SINGLE_FP_CONFIG</code>,
<code>CL_DEVICE_HALF_FP_CONFIG</code>, and <code>CL_DEVICE_DOUBLE_FP_CONFIG</code> device queries.</p>
</div>
</div>
<div class="sect2">
<h3 id="_floating_point_exceptions">6.5. Floating-Point Exceptions</h3>
<div class="paragraph">
<p>Floating-point exceptions are disabled in OpenCL.
The result of a floating-point exception must match the IEEE 754 spec for
the exceptions-not-enabled case.
Whether and when the implementation sets floating-point flags or raises
floating-point exceptions is implementation-defined.</p>
</div>
<div class="paragraph">
<p>This standard provides no method for querying, clearing or setting
floating-point flags or trapping raised exceptions.
Due to non-performance, non-portability of trap mechanisms, and the
impracticality of servicing precise exceptions in a vector context
(especially on heterogeneous hardware), such features are discouraged.</p>
</div>
<div class="paragraph">
<p>Implementations that nevertheless support such operations through an
extension to the standard shall initialize with all exception flags cleared
and the exception masks set so that exceptions raised by arithmetic
operations do not trigger a trap to be taken.
If the underlying work is reused by the implementation, the implementation
is however not responsible for re-clearing the flags or resetting exception
masks to default values before entering the kernel.
That is to say that kernels that do not inspect flags or enable traps are
licensed to expect that their arithmetic will not trigger a trap.
Those kernels that do examine flags or enable traps are responsible for
clearing flag state and disabling all traps before returning control to the
implementation.
Whether or when the underlying work-item (and accompanying global
floating-point state if any) is reused is implementation-defined.</p>
</div>
</div>
<div class="sect2">
<h3 id="relative-error-as-ulps">6.6. Relative Error as ULPs</h3>
<div class="paragraph">
<p>In this section we discuss the maximum relative error defined as ulp (units
in the last place).
Addition, subtraction, multiplication, fused multiply-add, and conversion
between integer and a single precision floating-point format are IEEE 754
compliant and are therefore correctly rounded.
Conversion between floating-point formats and explicit conversions must be
correctly rounded.</p>
</div>
<div class="paragraph">
<p>The ULP is defined as follows:</p>
</div>
<div class="quoteblock">
<blockquote>
<div class="paragraph">
<p>If x is a real number that lies between two finite consecutive
floating-point numbers a and b, without being equal to one of them, then
ulp(x) = |b - a|, otherwise ulp(x) is the distance between the two non-equal
finite floating-point numbers nearest x.
Moreover, ulp(NaN) is NaN.</p>
</div>
</blockquote>
</div>
<div class="paragraph">
<p>Attribution: This definition was taken with consent from Jean-Michel Muller
with slight clarification for behavior at zero. Refer to: <a href="#ulp-definition">On the definition of ulp(x)</a>.</p>
</div>
<div class="paragraph">
<p>0 ULP is used for math functions that do not require rounding.
The reference value used to compute the ULP value is the infinitely precise
result.</p>
</div>
<div class="sect3">
<h4 id="_ulp_values_for_math_instructions_full_profile">6.6.1. ULP Values for Math Instructions - Full Profile</h4>
<div class="paragraph">
<p>The ULP Values for Math Instructions table below describes the minimum
accuracy of floating-point math arithmetic instructions for full profile
devices given as ULP values.</p>
</div>
<table id="ulp_values_for_math_instructions" class="tableblock frame-all grid-all stretch">
<caption class="title">Table 5. ULP Values for Math Instructions - Full Profile</caption>
<colgroup>
<col style="width: 31%;">
<col style="width: 23%;">
<col style="width: 23%;">
<col style="width: 23%;">
</colgroup>
<thead>
<tr>
<th class="tableblock halign-left valign-top"><strong>SPIR-V Instruction</strong></th>
<th class="tableblock halign-left valign-top"><strong>Minimum Accuracy - Float64</strong></th>
<th class="tableblock halign-left valign-top"><strong>Minimum Accuracy - Float32</strong></th>
<th class="tableblock halign-left valign-top"><strong>Minimum Accuracy - Float16</strong></th>
</tr>
</thead>
<tbody>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpFAdd</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpFSub</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpFMul</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpFDiv</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 2.5 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>acos</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 2 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>acosh</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 2 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>acospi</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 5 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 5 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 2 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>asin</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 2 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>asinh</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 2 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>asinpi</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 5 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 5 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 2 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>atan</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 5 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 5 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 2 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>atanh</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 5 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 5 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 2 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>atanpi</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 5 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 5 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 2 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>atan2</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 6 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 6 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 2 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>atan2pi</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 6 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 6 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 2 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>cbrt</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 2 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 2 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 2 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>ceil</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>copysign</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>cos</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 2 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>cosh</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 2 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>cospi</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 2 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>cross</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">absolute error tolerance of 'max * max * (3 * HLF_EPSILON)' per vector component, where <em>max</em> is the maximum input operand magnitude</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">absolute error tolerance of 'max * max * (3 * FLT_EPSILON)' per vector component, where <em>max</em> is the maximum input operand magnitude</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">absolute error tolerance of 'max * max * (3 * FLT_EPSILON)' per vector component, where <em>max</em> is the maximum input operand magnitude</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>degrees</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 2 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 2 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 2 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>distance</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 2n ulp, for gentype with vector width <em>n</em></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 2.5 + 2n ulp, for gentype with vector width <em>n</em></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 5.5 + 2n ulp, for gentype with vector width <em>n</em></p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>dot</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">absolute error tolerance of 'max * max * (2n - 1) * HLF_EPSILON', for vector width <em>n</em> and maximum input operand magnitude <em>max</em> across all vector components</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">absolute error tolerance of 'max * max * (2n - 1) * FLT_EPSILON', for vector width <em>n</em> and maximum input operand magnitude <em>max</em> across all vector components</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">absolute error tolerance of 'max * max * (2n - 1) * FLT_EPSILON', for vector width <em>n</em> and maximum input operand magnitude <em>max</em> across all vector components</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>erfc</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 16 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 16 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>erf</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 16 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 16 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>exp</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 3 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 3 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 2 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>exp2</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 3 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 3 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 2 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>exp10</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 3 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 3 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 2 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>expm1</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 3 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 3 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 2 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>fabs</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>fclamp</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>fdim</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>floor</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>fma</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>fmax</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>fmax_common</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>fmin</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>fmin_common</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>fmod</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>fract</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>frexp</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>hypot</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 2 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>ilogb</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>ldexp</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>length</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 0.25 + 0.5n ulp, for gentype with vector width <em>n</em></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 2.75 + 0.5n ulp, for gentype with vector width <em>n</em></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 5.5 + n ulp, for gentype with vector width <em>n</em></p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>lgamma</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Implementation-defined</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Implementation-defined</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Implementation-defined</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>lgamma_r</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Implementation-defined</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Implementation-defined</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Implementation-defined</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>log</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 3 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 3 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 2 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>log2</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 3 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 3 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 2 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>log10</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 3 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 3 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 2 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>log1p</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 2 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 2 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 2 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>logb</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>mad</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Implemented either as a correctly rounded fma, or as a multiply followed
by an add, both of which are correctly rounded</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Implemented either as a correctly rounded fma, or as a multiply followed
by an add, both of which are correctly rounded</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Implemented either as a correctly rounded fma, or as a multiply followed
by an add, both of which are correctly rounded</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>maxmag</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>minmag</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>mix</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Implementation-defined</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">absolute error tolerance of 1e-3</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Implementation-defined</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>modf</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>nan</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>nextafter</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>normalize</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 1 + n ulp, for gentype with vector width <em>n</em></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 2 + n ulp, for gentype with vector width <em>n</em></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4.5 + n ulp, for gentype with vector width <em>n</em></p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>pow</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 16 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 16 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>pown</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 16 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 16 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>powr</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 16 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 16 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>radians</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 2 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 2 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 2 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>remainder</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>remquo</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp for the remainder, at least the lower 7 bits of the integral quotient</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp for the remainder, at least the lower 7 bits of the integral quotient</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp for the remainder, at least the lower 7 bits of the integral quotient</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>rint</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>rootn</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 16 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 16 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>round</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>rsqrt</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 2 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 2 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 1 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>sign</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>sin</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 2 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>sincos</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp for sine and cosine values</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp for sine and cosine values</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 2 ulp for sine and cosine values</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>sinh</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 2 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>sinpi</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 2 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>smoothstep</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Implementation-defined</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">absolute error tolerance of 1e-5</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Implementation-defined</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>sqrt</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 3 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>step</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>tan</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 5 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 5 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 2 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>tanh</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 5 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 5 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 2 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>tanpi</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 6 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 6 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 2 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>tgamma</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 16 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 16 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>trunc</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>half_cos</strong></p></td>
<td class="tableblock halign-left valign-top"></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 8192 ulp</p></td>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>half_divide</strong></p></td>
<td class="tableblock halign-left valign-top"></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 8192 ulp</p></td>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>half_exp</strong></p></td>
<td class="tableblock halign-left valign-top"></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 8192 ulp</p></td>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>half_exp2</strong></p></td>
<td class="tableblock halign-left valign-top"></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 8192 ulp</p></td>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>half_exp10</strong></p></td>
<td class="tableblock halign-left valign-top"></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 8192 ulp</p></td>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>half_log</strong></p></td>
<td class="tableblock halign-left valign-top"></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 8192 ulp</p></td>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>half_log2</strong></p></td>
<td class="tableblock halign-left valign-top"></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 8192 ulp</p></td>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>half_log10</strong></p></td>
<td class="tableblock halign-left valign-top"></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 8192 ulp</p></td>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>half_powr</strong></p></td>
<td class="tableblock halign-left valign-top"></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 8192 ulp</p></td>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>half_recip</strong></p></td>
<td class="tableblock halign-left valign-top"></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 8192 ulp</p></td>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>half_rsqrt</strong></p></td>
<td class="tableblock halign-left valign-top"></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 8192 ulp</p></td>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>half_sin</strong></p></td>
<td class="tableblock halign-left valign-top"></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 8192 ulp</p></td>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>half_sqrt</strong></p></td>
<td class="tableblock halign-left valign-top"></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 8192 ulp</p></td>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>half_tan</strong></p></td>
<td class="tableblock halign-left valign-top"></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 8192 ulp</p></td>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>fast_distance</strong></p></td>
<td class="tableblock halign-left valign-top"></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 8191.5 + 2n ulp, for gentype with vector width <em>n</em></p></td>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>fast_length</strong></p></td>
<td class="tableblock halign-left valign-top"></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 8191.5 + n ulp, for gentype with vector width <em>n</em></p></td>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>fast_normalize</strong></p></td>
<td class="tableblock halign-left valign-top"></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 8192 + n ulp, for gentype with vector width <em>n</em></p></td>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>native_cos</strong></p></td>
<td class="tableblock halign-left valign-top"></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Implementation-defined</p></td>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>native_divide</strong></p></td>
<td class="tableblock halign-left valign-top"></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Implementation-defined</p></td>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>native_exp</strong></p></td>
<td class="tableblock halign-left valign-top"></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Implementation-defined</p></td>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>native_exp2</strong></p></td>
<td class="tableblock halign-left valign-top"></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Implementation-defined</p></td>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>native_exp10</strong></p></td>
<td class="tableblock halign-left valign-top"></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Implementation-defined</p></td>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>native_log</strong></p></td>
<td class="tableblock halign-left valign-top"></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Implementation-defined</p></td>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>native_log2</strong></p></td>
<td class="tableblock halign-left valign-top"></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Implementation-defined</p></td>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>native_log10</strong></p></td>
<td class="tableblock halign-left valign-top"></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Implementation-defined</p></td>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>native_powr</strong></p></td>
<td class="tableblock halign-left valign-top"></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Implementation-defined</p></td>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>native_recip</strong></p></td>
<td class="tableblock halign-left valign-top"></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Implementation-defined</p></td>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>native_rsqrt</strong></p></td>
<td class="tableblock halign-left valign-top"></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Implementation-defined</p></td>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>native_sin</strong></p></td>
<td class="tableblock halign-left valign-top"></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Implementation-defined</p></td>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>native_sqrt</strong></p></td>
<td class="tableblock halign-left valign-top"></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Implementation-defined</p></td>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>native_tan</strong></p></td>
<td class="tableblock halign-left valign-top"></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Implementation-defined</p></td>
<td class="tableblock halign-left valign-top"></td>
</tr>
</tbody>
</table>
</div>
<div class="sect3">
<h4 id="_ulp_values_for_math_instructions_embedded_profile">6.6.2. ULP Values for Math Instructions - Embedded Profile</h4>
<div class="paragraph">
<p>The ULP Values for Math instructions for Embedded Profile table below
describes the minimum accuracy of floating-point math arithmetic operations
given as ULP values for the embedded profile.</p>
</div>
<table id="ulp_values_for_math_instructions_for_embedded_profile" class="tableblock frame-all grid-all stretch">
<caption class="title">Table 6. ULP Values for Math Instructions - Embedded Profile</caption>
<colgroup>
<col style="width: 31%;">
<col style="width: 23%;">
<col style="width: 23%;">
<col style="width: 23%;">
</colgroup>
<thead>
<tr>
<th class="tableblock halign-left valign-top"><strong>SPIR-V Instruction</strong></th>
<th class="tableblock halign-left valign-top"><strong>Minimum Accuracy - Float64</strong></th>
<th class="tableblock halign-left valign-top"><strong>Minimum Accuracy - Float32</strong></th>
<th class="tableblock halign-left valign-top"><strong>Minimum Accuracy - Float16</strong></th>
</tr>
</thead>
<tbody>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpFAdd</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpFSub</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpFMul</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpFDiv</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 3 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 3 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 1 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>acos</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 3 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>acosh</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 3 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>acospi</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 5 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 5 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 3 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>asin</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 3 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>asinh</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 3 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>asinpi</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 5 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 5 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 3 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>atan</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 5 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 5 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 3 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>atanh</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 5 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 5 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 3 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>atanpi</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 5 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 5 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 3 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>atan2</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 6 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 6 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 3 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>atan2pi</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 6 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 6 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 3 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>cbrt</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 2 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>ceil</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>copysign</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>cos</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 2 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>cosh</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 3 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>cospi</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 2 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>degrees</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 2 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 2 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 2 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>erfc</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 16 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 16 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>erf</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 16 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 16 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>exp</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 3 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>exp2</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 3 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>exp10</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 3 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>expm1</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 3 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>fabs</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>fclamp</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>fdim</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>floor</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>fma</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>fmax</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>fmax_common</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>fmin</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>fmin_common</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>fmod</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>fract</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>frexp</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>hypot</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 3 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>ilogb</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>ldexp</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>lgamma</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Implementation-defined</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Implementation-defined</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Implementation-defined</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>lgamma_r</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Implementation-defined</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Implementation-defined</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Implementation-defined</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>log</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 3 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>log2</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 3 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>log10</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 3 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>log1p</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 3 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>logb</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>mad</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Implementation-defined</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Implementation-defined</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Implementation-defined</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>maxmag</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>minmag</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>mix</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Implementation-defined</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Implementation-defined</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Implementation-defined</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>modf</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>nan</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>nextafter</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>pow</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 16 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 16 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 5 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>pown</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 16 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 16 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 5 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>powr</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 16 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 16 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 5 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>radians</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 2 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 2 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 2 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>remainder</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>remquo</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp for the remainder, at least the lower 7 bits of the integral quotient</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp for the remainder, at least the lower 7 bits of the integral quotient</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp for the remainder, at least the lower 7 bits of the integral quotient</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>rint</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>rootn</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 16 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 16 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 5 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>round</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>rsqrt</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 1 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>sign</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>sin</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 2 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>sincos</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp for sine and cosine values</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp for sine and cosine values</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 2 ulp for sine and cosine values</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>sinh</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 3 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>sinpi</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 2 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>smoothstep</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Implementation-defined</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Implementation-defined</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Implementation-defined</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>sqrt</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 1 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>step</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">0 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>tan</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 5 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 5 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 3 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>tanh</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 5 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 5 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 3 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>tanpi</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 6 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 6 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 3 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>tgamma</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 16 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 16 ulp</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>trunc</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Correctly rounded</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>half_cos</strong></p></td>
<td class="tableblock halign-left valign-top"></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 8192 ulp</p></td>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>half_divide</strong></p></td>
<td class="tableblock halign-left valign-top"></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 8192 ulp</p></td>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>half_exp</strong></p></td>
<td class="tableblock halign-left valign-top"></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 8192 ulp</p></td>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>half_exp2</strong></p></td>
<td class="tableblock halign-left valign-top"></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 8192 ulp</p></td>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>half_exp10</strong></p></td>
<td class="tableblock halign-left valign-top"></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 8192 ulp</p></td>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>half_log</strong></p></td>
<td class="tableblock halign-left valign-top"></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 8192 ulp</p></td>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>half_log2</strong></p></td>
<td class="tableblock halign-left valign-top"></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 8192 ulp</p></td>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>half_log10</strong></p></td>
<td class="tableblock halign-left valign-top"></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 8192 ulp</p></td>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>half_powr</strong></p></td>
<td class="tableblock halign-left valign-top"></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 8192 ulp</p></td>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>half_recip</strong></p></td>
<td class="tableblock halign-left valign-top"></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 8192 ulp</p></td>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>half_rsqrt</strong></p></td>
<td class="tableblock halign-left valign-top"></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 8192 ulp</p></td>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>half_sin</strong></p></td>
<td class="tableblock halign-left valign-top"></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 8192 ulp</p></td>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>half_sqrt</strong></p></td>
<td class="tableblock halign-left valign-top"></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 8192 ulp</p></td>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>half_tan</strong></p></td>
<td class="tableblock halign-left valign-top"></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 8192 ulp</p></td>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>native_cos</strong></p></td>
<td class="tableblock halign-left valign-top"></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Implementation-defined</p></td>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>native_divide</strong></p></td>
<td class="tableblock halign-left valign-top"></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Implementation-defined</p></td>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>native_exp</strong></p></td>
<td class="tableblock halign-left valign-top"></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Implementation-defined</p></td>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>native_exp2</strong></p></td>
<td class="tableblock halign-left valign-top"></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Implementation-defined</p></td>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>native_exp10</strong></p></td>
<td class="tableblock halign-left valign-top"></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Implementation-defined</p></td>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>native_log</strong></p></td>
<td class="tableblock halign-left valign-top"></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Implementation-defined</p></td>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>native_log2</strong></p></td>
<td class="tableblock halign-left valign-top"></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Implementation-defined</p></td>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>native_log10</strong></p></td>
<td class="tableblock halign-left valign-top"></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Implementation-defined</p></td>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>native_powr</strong></p></td>
<td class="tableblock halign-left valign-top"></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Implementation-defined</p></td>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>native_recip</strong></p></td>
<td class="tableblock halign-left valign-top"></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Implementation-defined</p></td>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>native_rsqrt</strong></p></td>
<td class="tableblock halign-left valign-top"></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Implementation-defined</p></td>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>native_sin</strong></p></td>
<td class="tableblock halign-left valign-top"></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Implementation-defined</p></td>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>native_sqrt</strong></p></td>
<td class="tableblock halign-left valign-top"></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Implementation-defined</p></td>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>native_tan</strong></p></td>
<td class="tableblock halign-left valign-top"></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Implementation-defined</p></td>
<td class="tableblock halign-left valign-top"></td>
</tr>
</tbody>
</table>
</div>
<div class="sect3">
<h4 id="_ulp_values_for_math_instructions_unsafe_math_optimizations_enabled">6.6.3. ULP Values for Math Instructions - Unsafe Math Optimizations Enabled</h4>
<div class="paragraph">
<p>The ULP Values for Math Instructions with Unsafe Math Optimizations table below
describes the minimum accuracy of commonly used single precision
floating-point math arithmetic instructions given as ULP values if the
<em>-cl-unsafe-math-optimizations</em> compiler option is specified when compiling or
building the OpenCL program.</p>
</div>
<div class="paragraph">
<p>For derived implementations, the operations used in the derivation may
themselves be relaxed according to the ULP Values for Math Instructions with
Unsafe Math Optimizations table.</p>
</div>
<div class="paragraph">
<p>The minimum accuracy of math functions not defined in the ULP Values for
Math Instructions with Unsafe Math Optimizations table when the
<em>-cl-unsafe-math-optimizations</em> compiler option is specified is as defined in the
<a href="#ulp_values_for_math_instructions">ULP Values for Math Instructions for Full
Profile</a> table when operating in the full profile, and as defined in the
<a href="#ulp_values_for_math_instructions_for_embedded_profile">ULP Values for Math
instructions for Embedded Profile</a> table when operating in the embedded
profile.</p>
</div>
<table id="ulp_values_for_math_instructions_with_fast_relaxed_math" class="tableblock frame-all grid-all stretch">
<caption class="title">Table 7. ULP Values for Single Precision Math Instructions with <em>-cl-unsafe-math-optimizations</em></caption>
<colgroup>
<col style="width: 30%;">
<col style="width: 70%;">
</colgroup>
<thead>
<tr>
<th class="tableblock halign-left valign-top"><strong>SPIR-V Instruction</strong></th>
<th class="tableblock halign-left valign-top"><strong>Minimum Accuracy</strong></th>
</tr>
</thead>
<tbody>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpFDiv</strong> for 1.0 / <em>x</em></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 2.5 ulp for x in the domain of 2<sup>-126</sup> to 2<sup>126</sup> for the full profile,
and &lt;= 3 ulp for the embedded profile.</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpFDiv</strong> for <em>x</em> / <em>y</em></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 2.5 ulp for x in the domain of 2<sup>-62</sup> to 2<sup>62</sup> and <em>y</em> in the domain
of 2<sup>-62</sup> to 2<sup>62</sup> for the full profile, and &lt;= 3 ulp for the embedded
profile.</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>acos</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4096 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>acosh</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Implemented as log( x + sqrt(x*x - 1) ).</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>acospi</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Implemented as acos(x) * M_PI_F.
For non-derived implementations, the error is &lt;= 8192 ulp.</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>asin</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4096 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>asinh</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Implemented as log( x + sqrt(x*x + 1) ).</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>asinpi</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Implemented as asin(x) * M_PI_F.
For non-derived implementations, the error is &lt;= 8192 ulp.</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>atan</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 4096 ulp</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>atanh</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Defined for x in the domain (-1, 1).
For x in [-2<sup>-10</sup>, 2<sup>-10</sup>], implemented as x.
For x outside of [-2<sup>-10</sup>, 2<sup>-10</sup>], implemented as 0.5f * log( (1.0f + x)
/ (1.0f - x) ).
For non-derived implementations, the error is &lt;= 8192 ulp.</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>atanpi</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Implemented as atan(x) * M_1_PI_F.
For non-derived implementations, the error is &lt;= 8192 ulp.</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>atan2</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Implemented as atan(y/x) for x &gt; 0, atan(y/x) + M_PI_F for x &lt; 0 and y &gt;
0, and atan(y/x) - M_PI_F for x &lt; 0 and y &lt; 0.</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>atan2pi</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Implemented as atan2(y, x) * M_1_PI_F.
For non-derived implementations, the error is &lt;= 8192 ulp.</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>cbrt</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Implemented as rootn(x, 3).
For non-derived implementations, the error is &lt;= 8192 ulp.</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>cos</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">For x in the domain [-π, π], the maximum absolute error is &lt;=
2<sup>-11</sup> and larger otherwise.</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>cosh</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Defined for x in the domain [-∞, ∞] and implemented as 0.5f * (
exp(x) + exp(-x) ).
For non-derived implementations, the error is &lt;= 8192 ULP.</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>cospi</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">For x in the domain [-1, 1], the maximum absolute error is &lt;= 2<sup>-11</sup> and
larger otherwise.</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>exp</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 3 + floor( fabs(2 * x) ) ulp for the full profile, and &lt;= 4 ulp for
the embedded profile.</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>exp2</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">&lt;= 3 + floor( fabs(2 * x) ) ulp for the full profile, and &lt;= 4 ulp for
the embedded profile.</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>exp10</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Derived implementations implement this as exp2( x * log2(10) ).
For non-derived implementations, the error is &lt;= 8192 ulp.</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>expm1</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Derived implementations implement this as exp(x) - 1.
For non-derived implementations, the error is &lt;= 8192 ulp.</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>log</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">For x in the domain [0.5, 2] the maximum absolute error is &lt;= 2<sup>-21</sup>;
otherwise the maximum error is &lt;=3 ulp for the full profile and &lt;= 4 ulp
for the embedded profile</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>log2</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">For x in the domain [0.5, 2] the maximum absolute error is &lt;= 2<sup>-21</sup>;
otherwise the maximum error is &lt;=3 ulp for the full profile and &lt;= 4 ulp
for the embedded profile</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>log10</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">For x in the domain [0.5, 2] the maximum absolute error is &lt;= 2<sup>-21</sup>;
otherwise the maximum error is &lt;=3 ulp for the full profile and &lt;= 4 ulp
for the embedded profile</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>log1p</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Derived implementations implement this as log(x + 1).
For non-derived implementations, the error is &lt;= 8192 ulp.</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>pow</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Undefined for x = 0 and y = 0.
Undefined for x &lt; 0 and non-integer y.
Undefined for x &lt; 0 and y outside the domain [-2<sup>24</sup>, 2<sup>24</sup>].
For x &gt; 0 or x &lt; 0 and even y, derived implementations implement this as
exp2( y * log2( fabs(x) ) ).
For x &lt; 0 and odd y, derived implementations implement this as -exp2( y *
log2( fabs(x) ).
For x == 0 and nonzero y, derived implementations return zero.
For non-derived implementations, the error is &lt;= 8192 ULP.</p>
<p class="tableblock"> On some implementations, powr() or pown() may perform faster
than pow().
If x is known to be &gt;= 0, consider using powr() in place of pow(),
or if y is known to be an integer, consider using pown() in place of
pow().</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>pown</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Defined only for integer values of y.
Undefined for x = 0 and y = 0.
For x &gt;= 0 or x &lt; 0 and even y, derived implementations implement this as
exp2( y * log2( fabs(x) ) ).
For x &lt; 0 and odd y, derived implementations implement this as -exp2( y *
log2( fabs(x) ) ).
For non-derived implementations, the error is &lt;= 8192 ulp.</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>powr</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Defined only for x &gt;= 0.
Undefined for x = 0 and y = 0.
Derived implementations implement this as exp2( y * log2(x) ).
For non-derived implementations, the error is &lt;= 8192 ulp.</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>rootn</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Defined for x &gt; 0 when y is non-zero, derived implementations implement
this case as exp2( log2(x) / y ).
Defined for x &lt; 0 when y is odd, derived implementations implement this
case as -exp2( log2(-x) / y ).
Defined for x = +/-0 when y &gt; 0, derived implementations will return +0 in
this case.
For non-derived implementations, the error is &lt;= 8192 ULP.</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>sin</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">For x in the domain [-π, π], the maximum absolute error is &lt;=
2<sup>-11</sup> and larger otherwise.</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>sincos</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">ulp values as defined for sin(x) and cos(x).</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>sinh</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Defined for x in the domain [-∞, ∞].
For x in [-2<sup>-10</sup>, 2<sup>-10</sup>], derived implementations implement as x.
For x outside of [-2<sup>-10</sup>, 2<sup>-10</sup>], derived implement as 0.5f * ( exp(x) -
exp(-x) ).
For non-derived implementations, the error is &lt;= 8192 ULP.</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>sinpi</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">For x in the domain [-1, 1], the maximum absolute error is &lt;= 2<sup>-11</sup> and
larger otherwise.</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>tan</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Derived implementations implement this as sin(x) * ( 1.0f / cos(x) ).
For non-derived implementations, the error is &lt;= 8192 ulp.</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>tanh</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Defined for x in the domain [-∞, ∞].
For x in [-2<sup>-10</sup>, 2<sup>-10</sup>], derived implementations implement as x.
For x outside of [-2<sup>-10</sup>, 2<sup>-10</sup>], derived implementations implement as
(exp(x) - exp(-x)) / (exp(x) + exp(-x)).
For non-derived implementations, the error is &lt;= 8192 ULP.</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpExtInst</strong> <strong>tanpi</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Derived implementations implement this as tan(x * M_PI_F).
For non-derived implementations, the error is &lt;= 8192 ulp for x in the
domain [-1, 1].</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpFMul</strong> and <strong>OpFAdd</strong>,<br>
for <em>x</em> * <em>y</em> + <em>z</em></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Implemented either as a correctly rounded fma or as a multiply and an add
both of which are correctly rounded.</p></td>
</tr>
</tbody>
</table>
</div>
</div>
<div class="sect2">
<h3 id="_edge_case_behavior">6.7. Edge Case Behavior</h3>
<div class="paragraph">
<p>The edge case behavior of the math functions shall conform to sections F.9
and G.6 of ISO/IEC 9899:TC 2, except where noted below in the
<em><a href="#additional-requirements-beyond-isoiec-9899tc2">Additional Requirements
Beyond ISO/IEC 9899:TC2</a> section</em>.</p>
</div>
<div class="sect3">
<h4 id="additional-requirements-beyond-isoiec-9899tc2">6.7.1. Additional Requirements Beyond ISO/IEC 9899:TC2</h4>
<div class="paragraph">
<p>All functions that return a NaN should return a quiet NaN.</p>
</div>
<div class="paragraph">
<p>The usual allowances for rounding error (<em><a href="#relative-error-as-ulps">Relative
Error as ULPs</a> section</em>) or flushing behavior
(<em><a href="#edge-case-behavior-in-flush-to-zero-mode">Edge Case Behavior in Flush To
Zero Mode</a> section</em>) shall not apply for those values for which <em>section
F.9</em> of ISO/IEC 9899:,TC2, or
<em><a href="#additional-requirements-beyond-isoiec-9899tc2">Additional Requirements
Beyond ISO/IEC 9899:TC2</a></em> and
<em><a href="#edge-case-behavior-in-flush-to-zero-mode">Edge Case Behavior in Flush To
Zero Mode</a> sections</em> below (and similar sections for other floating-point
precisions) prescribe a result (e.g. ceil( -1 &lt; x &lt; 0 ) returns -0).
Those values shall produce exactly the prescribed answers, and no other.
Where the ± symbol is used, the sign shall be preserved.
For example, sin(±0) = ±0 shall be interpreted to mean sin(+0)
is +0 and sin(-0) is -0.</p>
</div>
<div class="ulist">
<ul>
<li>
<p><strong>OpExtInst</strong> <strong>acospi</strong>:</p>
<div class="ulist">
<ul>
<li>
<p>acospi( 1 ) = +0.</p>
</li>
<li>
<p>acospi( x ) returns a NaN for | x | &gt; 1.</p>
</li>
</ul>
</div>
</li>
<li>
<p><strong>OpExtInst</strong> <strong>asinpi</strong>:</p>
<div class="ulist">
<ul>
<li>
<p>asinpi( ±0 ) = ±0.</p>
</li>
<li>
<p>asinpi( x ) returns a NaN for | x | &gt; 1.</p>
</li>
</ul>
</div>
</li>
<li>
<p><strong>OpExtInst</strong> <strong>atanpi</strong>:</p>
<div class="ulist">
<ul>
<li>
<p>atanpi( ±0 ) = ±0.</p>
</li>
<li>
<p>atanpi ( ±∞ ) = ±0.5.</p>
</li>
</ul>
</div>
</li>
<li>
<p><strong>OpExtInst</strong> <strong>atan2pi</strong>:</p>
<div class="ulist">
<ul>
<li>
<p>atan2pi ( ±0, -0 ) = ±1.</p>
</li>
<li>
<p>atan2pi ( ±0, +0 ) = ± 0.</p>
</li>
<li>
<p>atan2pi ( ±0, x ) returns ± 1 for x &lt; 0.</p>
</li>
<li>
<p>atan2pi ( ±0, x) returns ± 0 for x &gt; 0.</p>
</li>
<li>
<p>atan2pi ( y, ±0 ) returns -0.5 for y &lt; 0.</p>
</li>
<li>
<p>atan2pi ( y, ±0 ) returns 0.5 for y &gt; 0.</p>
</li>
<li>
<p>atan2pi ( ±y, -∞ ) returns ± 1 for finite y &gt; 0.</p>
</li>
<li>
<p>atan2pi ( ±y, +∞ ) returns ± 0 for finite y &gt; 0.</p>
</li>
<li>
<p>atan2pi ( ±∞, x ) returns ± 0.5 for finite x.</p>
</li>
<li>
<p>atan2pi (±∞, -∞ ) returns ±0.75.</p>
</li>
<li>
<p>atan2pi (±∞, +∞ ) returns ±0.25.</p>
</li>
</ul>
</div>
</li>
<li>
<p><strong>OpExtInst</strong> <strong>ceil</strong>:</p>
<div class="ulist">
<ul>
<li>
<p>ceil( -1 &lt; x &lt; 0 ) returns -0.</p>
</li>
</ul>
</div>
</li>
<li>
<p><strong>OpExtInst</strong> <strong>cospi</strong>:</p>
<div class="ulist">
<ul>
<li>
<p>cospi( ±0 ) returns 1</p>
</li>
<li>
<p>cospi( n + 0.5 ) is +0 for any integer n where n + 0.5 is
representable.</p>
</li>
<li>
<p>cospi( ±∞ ) returns a NaN.</p>
</li>
</ul>
</div>
</li>
<li>
<p><strong>OpExtInst</strong> <strong>exp10</strong>:</p>
<div class="ulist">
<ul>
<li>
<p>exp10( ±0 ) returns 1.</p>
</li>
<li>
<p>exp10( -∞ ) returns +0.</p>
</li>
<li>
<p>exp10( +∞ ) returns +∞.</p>
</li>
</ul>
</div>
</li>
<li>
<p><strong>OpExtInst</strong> <strong>distance</strong>:</p>
<div class="ulist">
<ul>
<li>
<p>distance(x, y) calculates the distance from x to y without overflow or
extraordinary precision loss due to underflow.</p>
</li>
</ul>
</div>
</li>
<li>
<p><strong>OpExtInst</strong> <strong>fdim</strong>:</p>
<div class="ulist">
<ul>
<li>
<p>fdim( any, NaN ) returns NaN.</p>
</li>
<li>
<p>fdim( NaN, any ) returns NaN.</p>
</li>
</ul>
</div>
</li>
<li>
<p><strong>OpExtInst</strong> <strong>fmod</strong>:</p>
<div class="ulist">
<ul>
<li>
<p>fmod( ±0, NaN ) returns NaN.</p>
</li>
</ul>
</div>
</li>
<li>
<p><strong>OpExtInst</strong> <strong>fract</strong>:</p>
<div class="ulist">
<ul>
<li>
<p>fract( x, iptr) shall not return a value greater than or equal to 1.0,
and shall not return a value less than 0.</p>
</li>
<li>
<p>fract( +0, iptr ) returns +0 and +0 in iptr.</p>
</li>
<li>
<p>fract( -0, iptr ) returns -0 and -0 in iptr.</p>
</li>
<li>
<p>fract( +inf, iptr ) returns +0 and +inf in iptr.</p>
</li>
<li>
<p>fract( -inf, iptr ) returns -0 and -inf in iptr.</p>
</li>
<li>
<p>fract( NaN, iptr ) returns the NaN and NaN in iptr.</p>
</li>
</ul>
</div>
</li>
<li>
<p><strong>OpExtInst</strong> <strong>frexp</strong>:</p>
<div class="ulist">
<ul>
<li>
<p>frexp( ±∞, exp ) returns ±∞ and stores 0 in exp.</p>
</li>
<li>
<p>frexp( NaN, exp ) returns the NaN and stores 0 in exp.</p>
</li>
</ul>
</div>
</li>
<li>
<p><strong>OpExtInst</strong> <strong>length</strong>:</p>
<div class="ulist">
<ul>
<li>
<p>length calculates the length of a vector without overflow or
extraordinary precision loss due to underflow.</p>
</li>
</ul>
</div>
</li>
<li>
<p><strong>OpExtInst</strong> <strong>lgamma_r</strong>:</p>
<div class="ulist">
<ul>
<li>
<p>lgamma_r( x, signp ) returns 0 in signp if x is zero or a negative
integer.</p>
</li>
</ul>
</div>
</li>
<li>
<p><strong>OpExtInst</strong> <strong>nextafter</strong>:</p>
<div class="ulist">
<ul>
<li>
<p>nextafter( -0, y &gt; 0 ) returns smallest positive denormal value.</p>
</li>
<li>
<p>nextafter( +0, y &lt; 0 ) returns smallest negative denormal value.</p>
</li>
</ul>
</div>
</li>
<li>
<p><strong>OpExtInst</strong> <strong>normalize</strong>:</p>
<div class="ulist">
<ul>
<li>
<p>normalize shall reduce the vector to unit length, pointing in the same
direction without overflow or extraordinary precision loss due to
underflow.</p>
</li>
<li>
<p>normalize( v ) returns v if all elements of v are zero.</p>
</li>
<li>
<p>normalize( v ) returns a vector full of NaNs if any element is a NaN.</p>
</li>
<li>
<p>normalize( v ) for which any element in v is infinite shall proceed as
if the elements in v were replaced as follows:</p>
<div class="listingblock">
<div class="content">
<pre class="CodeRay highlight"><code>for( i = 0; i &lt; sizeof(v) / sizeof(v[0] ); i++ )
v[i] = isinf(v[i] ) ? copysign(1.0, v[i]) : 0.0 * v [i];</code></pre>
</div>
</div>
</li>
</ul>
</div>
</li>
<li>
<p><strong>OpExtInst</strong> <strong>pow</strong>:</p>
<div class="ulist">
<ul>
<li>
<p>pow( ±0, -∞ ) returns +∞</p>
</li>
</ul>
</div>
</li>
<li>
<p><strong>OpExtInst</strong> <strong>pown</strong>:</p>
<div class="ulist">
<ul>
<li>
<p>pown( x, 0 ) is 1 for any x, even zero, NaN or infinity.</p>
</li>
<li>
<p>pown( ±0, n ) is ±∞ for odd n &lt; 0.</p>
</li>
<li>
<p>pown( ±0, n ) is +∞ for even n &lt; 0.</p>
</li>
<li>
<p>pown( ±0, n ) is +0 for even n &gt; 0.</p>
</li>
<li>
<p>pown( ±0, n ) is ±0 for odd n &gt; 0.</p>
</li>
</ul>
</div>
</li>
<li>
<p><strong>OpExtInst</strong> <strong>powr</strong>:</p>
<div class="ulist">
<ul>
<li>
<p>powr( x, ±0 ) is 1 for finite x &gt; 0.</p>
</li>
<li>
<p>powr( ±0, y ) is +∞ for finite y &lt; 0.</p>
</li>
<li>
<p>powr( ±0, -∞) is +∞.</p>
</li>
<li>
<p>powr( ±0, y ) is +0 for y &gt; 0.</p>
</li>
<li>
<p>powr( +1, y ) is 1 for finite y.</p>
</li>
<li>
<p>powr( x, y ) returns NaN for x &lt; 0.</p>
</li>
<li>
<p>powr( ±0, ±0 ) returns NaN.</p>
</li>
<li>
<p>powr( +∞, ±0 ) returns NaN.</p>
</li>
<li>
<p>powr( +1, ±∞ ) returns NaN.</p>
</li>
<li>
<p>powr( x, NaN ) returns the NaN for x &gt;= 0.</p>
</li>
<li>
<p>powr( NaN, y ) returns the NaN.</p>
</li>
</ul>
</div>
</li>
<li>
<p><strong>OpExtInst</strong> <strong>rint</strong>:</p>
<div class="ulist">
<ul>
<li>
<p>rint( -0.5 &lt;= x &lt; 0 ) returns -0.</p>
</li>
</ul>
</div>
</li>
<li>
<p><strong>OpExtInst</strong> <strong>remquo</strong>:</p>
<div class="ulist">
<ul>
<li>
<p>remquo(x, y, &amp;quo) returns a NaN and 0 in quo if x is ±∞, or
if y is 0 and the other argument is non-NaN or if either argument is a
NaN.</p>
</li>
</ul>
</div>
</li>
<li>
<p><strong>OpExtInst</strong> <strong>rootn</strong>:</p>
<div class="ulist">
<ul>
<li>
<p>rootn( ±0, n ) is ±∞ for odd n &lt; 0.</p>
</li>
<li>
<p>rootn( ±0, n ) is +∞ for even n &lt; 0.</p>
</li>
<li>
<p>rootn( ±0, n ) is +0 for even n &gt; 0.</p>
</li>
<li>
<p>rootn( ±0, n ) is ±0 for odd n &gt; 0.</p>
</li>
<li>
<p>rootn( x, n ) returns a NaN for x &lt; 0 and n is even.</p>
</li>
<li>
<p>rootn( x, 0 ) returns a NaN.</p>
</li>
</ul>
</div>
</li>
<li>
<p><strong>OpExtInst</strong> <strong>round</strong>:</p>
<div class="ulist">
<ul>
<li>
<p>round( -0.5 &lt; x &lt; 0 ) returns -0.</p>
</li>
</ul>
</div>
</li>
<li>
<p><strong>OpExtInst</strong> <strong>sinpi</strong>:</p>
<div class="ulist">
<ul>
<li>
<p>sinpi( ±0 ) returns ±0.</p>
</li>
<li>
<p>sinpi( +n) returns +0 for positive integers n.</p>
</li>
<li>
<p>sinpi( -n ) returns -0 for negative integers n.</p>
</li>
<li>
<p>sinpi( ±∞ ) returns a NaN.</p>
</li>
</ul>
</div>
</li>
<li>
<p><strong>OpExtInst</strong> <strong>tanpi</strong>:</p>
<div class="ulist">
<ul>
<li>
<p>tanpi( ±0 ) returns ±0.</p>
</li>
<li>
<p>tanpi( ±∞ ) returns a NaN.</p>
</li>
<li>
<p>tanpi( n ) is copysign( 0.0, n ) for even integers n.</p>
</li>
<li>
<p>tanpi( n ) is copysign( 0.0, - n) for odd integers n.</p>
</li>
<li>
<p>tanpi( n + 0.5 ) for even integer n is +∞ where n + 0.5 is
representable.</p>
</li>
<li>
<p>tanpi( n + 0.5 ) for odd integer n is -∞ where n + 0.5 is
representable.</p>
</li>
</ul>
</div>
</li>
<li>
<p><strong>OpExtInst</strong> <strong>trunc</strong>:</p>
<div class="ulist">
<ul>
<li>
<p>trunc( -1 &lt; x &lt; 0 ) returns -0.</p>
</li>
</ul>
</div>
</li>
</ul>
</div>
</div>
<div class="sect3">
<h4 id="changes-to-isoiec-9899-tc2-behavior">6.7.2. Changes to ISO/IEC 9899: TC2 Behavior</h4>
<div class="paragraph">
<p><strong>OpExtInst</strong> <strong>modf</strong> behaves as though implemented by:</p>
</div>
<div class="listingblock">
<div class="content">
<pre class="CodeRay highlight"><code>gentype modf( gentype value, gentype *iptr )
{
*iptr = trunc( value );
return copysign( isinf( value ) ? 0.0 : value - *iptr, value );
}</code></pre>
</div>
</div>
<div class="paragraph">
<p><strong>OpExtInst</strong> <strong>rint</strong> always rounds according to round to nearest even rounding
mode even if the caller is in some other rounding mode.</p>
</div>
</div>
<div class="sect3">
<h4 id="edge-case-behavior-in-flush-to-zero-mode">6.7.3. Edge Case Behavior in Flush To Zero Mode</h4>
<div class="paragraph">
<p>If denormals are flushed to zero, then a function may return one of four
results:</p>
</div>
<div class="olist arabic">
<ol class="arabic">
<li>
<p>Any conforming result for non-flush-to-zero mode.</p>
</li>
<li>
<p>If the result given by 1 is a sub-normal before rounding, it may be
flushed to zero.</p>
</li>
<li>
<p>Any non-flushed conforming result for the function if one or more of its
sub-normal operands are flushed to zero.</p>
</li>
<li>
<p>If the result of 3 is a sub-normal before rounding, the result may be
flushed to zero.</p>
</li>
</ol>
</div>
<div class="paragraph">
<p>In each of the above cases, if an operand or result is flushed to zero, the
sign of the zero is undefined.</p>
</div>
<div class="paragraph">
<p>If subnormals are flushed to zero, a device may choose to conform to the
following edge cases for <strong>OpExtInst</strong> <strong>nextafter</strong> instead of those listed in
<em><a href="#additional-requirements-beyond-isoiec-9899tc2">Additional Requirements
Beyond ISO/IEC 9899:TC2</a> section</em>:</p>
</div>
<div class="ulist">
<ul>
<li>
<p>nextafter ( +smallest normal, y &lt; +smallest normal ) = +0.</p>
</li>
<li>
<p>nextafter ( -smallest normal, y &gt; -smallest normal ) = -0.</p>
</li>
<li>
<p>nextafter ( -0, y &gt; 0 ) returns smallest positive normal value.</p>
</li>
<li>
<p>nextafter ( +0, y &lt; 0 ) returns smallest negative normal value.</p>
</li>
</ul>
</div>
<div class="paragraph">
<p>For clarity, subnormals or denormals are defined to be the set of
representable numbers in the range 0 &lt; x &lt; TYPE_MIN and -TYPE_MIN &lt; x &lt; -0.
They do not include ±0.
A non-zero number is said to be sub-normal before rounding if, after
normalization, its radix-2 exponent is less than (TYPE_MIN_EXP - 1).
<sup class="footnote">[<a id="_footnoteref_1" class="footnote" href="#_footnotedef_1" title="View footnote.">1</a>]</sup></p>
</div>
</div>
</div>
</div>
</div>
<div class="sect1">
<h2 id="image_addressing_and_filtering">7. Image Addressing and Filtering</h2>
<div class="sectionbody">
<div class="paragraph">
<p>This section describes how image operations behave in an OpenCL environment.</p>
</div>
<div class="sect2">
<h3 id="image-coordinates">7.1. Image Coordinates</h3>
<div class="paragraph">
<p>Let <code>w<sub>t</sub></code>, <code>h<sub>t</sub></code> and <code>d<sub>t</sub></code> be the width, height (or image array size for a 1D image array) and depth (or image array size for a 2D image array) of the image in pixels.
Let <code>coord.xy</code> (also referred to as <code>(s,t)</code>) or <code>coord.xyz</code> (also referred to as <code>(s,t,r)</code>) be the coordinates specified to an image read instruction (such as <strong>OpImageRead</strong>) or an image write instruction (such as <strong>OpImageWrite</strong>).</p>
</div>
<div class="paragraph">
<p>If image coordinates specified to an image read instruction are normalized (as specified in the sampler), the <code>s</code>, <code>t</code>, and <code>r</code> coordinate values are multiplied by <code>w<sub>t</sub></code>, <code>h<sub>t</sub></code> and <code>d<sub>t</sub></code> respectively to generate the unnormalized coordinate values.
For image arrays, the image array coordinate (i.e. <code>t</code> if it is a 1D image array or <code>r</code> if it is a 2D image array) specified to the image read instruction must always be the unnormalized image coordinate value.</p>
</div>
<div class="paragraph">
<p>Image coordinates specified to an image write instruction are always unnormalized image coordinate values.</p>
</div>
<div class="paragraph">
<p>Let <code>(u,v,w)</code> represent the unnormalized image coordinate values.</p>
</div>
<div class="paragraph">
<p>If values in <code>(s,t,r)</code> or <code>(u,v,w)</code> are INF or NaN, the behavior of the image read instruction or image write instruction is undefined.</p>
</div>
</div>
<div class="sect2">
<h3 id="addressing-and-filter-modes">7.2. Addressing and Filter Modes</h3>
<div class="paragraph">
<p>After generating the image coordinate <code>(u,v,w)</code> we apply the appropriate addressing and filter mode to generate the appropriate sample locations to read from the image.</p>
</div>
<div class="sect3">
<h4 id="clamp-addressing">7.2.1. Clamp and None Addressing Modes</h4>
<div class="paragraph">
<p>We first describe how the addressing and filter modes are applied to generate the appropriate sample locations to read from the image if the addressing mode is <code>CL_ADDRESS_CLAMP</code>, <code>CL_ADDRESS_CLAMP_TO_EDGE</code>, or <code>CL_ADDRESS_NONE</code>.</p>
</div>
<div class="sect4">
<h5 id="clamp-nearest_filtering">Nearest Filtering</h5>
<div class="paragraph">
<p>When the filter mode is <code>CL_FILTER_NEAREST</code>, the result of the image read instruction is the image element that is nearest (in Manhattan distance) to the image element location <code>(i,j,k)</code>.
The image element location <code>(i,j,k)</code> is computed as:</p>
</div>
<div class="stemblock">
<div class="content">
\[\begin{aligned}
i &amp; = address\_mode((int)floor(u))\\
j &amp; = address\_mode((int)floor(v))\\
k &amp; = address\_mode((int)floor(w))
\end{aligned}\]
</div>
</div>
<div class="paragraph">
<p>For a 3D image, the image element at location <code>(i,j,k)</code> becomes the color value.
For a 2D image, the image element at location <code>(i,j)</code> becomes the color value.</p>
</div>
<div class="paragraph">
<p>The below table describes the <code>address_mode</code> function.</p>
</div>
<table id="addressing_modes_to_generate_texel_location" class="tableblock frame-all grid-all stretch">
<caption class="title">Table 8. Addressing Modes to Generate Texel Location</caption>
<colgroup>
<col style="width: 50%;">
<col style="width: 50%;">
</colgroup>
<thead>
<tr>
<th class="tableblock halign-left valign-top"><strong>Addressing Mode</strong></th>
<th class="tableblock halign-left valign-top"><strong>Result of <em>address_mode(coord)</em></strong></th>
</tr>
</thead>
<tbody>
<tr>
<td class="tableblock halign-left valign-top"><div class="content"><div class="paragraph">
<p><code>CL_ADDRESS_CLAMP</code></p>
</div></div></td>
<td class="tableblock halign-left valign-top"><div class="content"><div class="paragraph">
<p><em>clamp (coord, -1, size)</em></p>
</div></div></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><div class="content"><div class="paragraph">
<p><code>CL_ADDRESS_CLAMP_TO_EDGE</code></p>
</div></div></td>
<td class="tableblock halign-left valign-top"><div class="content"><div class="paragraph">
<p><em>clamp (coord, 0, size - 1)</em></p>
</div></div></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><div class="content"><div class="paragraph">
<p><code>CL_ADDRESS_NONE</code></p>
</div></div></td>
<td class="tableblock halign-left valign-top"><div class="content"><div class="paragraph">
<p><em>coord</em></p>
</div></div></td>
</tr>
</tbody>
</table>
<div class="paragraph">
<p>The size term in the table above is <code>w<sub>t</sub></code> for u, <code>h<sub>t</sub></code> for v and <code>d<sub>t</sub></code> for w.</p>
</div>
<div class="paragraph">
<p>The clamp function used in the table above is defined as:</p>
</div>
<div class="stemblock">
<div class="content">
\[\begin{aligned}
clamp(a, b, c) &amp; = return (a &lt; b) ? b : ((a &gt; c) ? c : a)
\end{aligned}\]
</div>
</div>
<div class="paragraph">
<p>If the addressing mode is <code>CL_ADDRESS_CLAMP</code> or <code>CL_ADDRESS_CLAMP_TO_EDGE</code>, and the selected texel location <code>(i,j,k)</code> refers to a location outside the image, the border color is used as the color value for the texel.</p>
</div>
<div class="paragraph">
<p>Otherwise, if the addressing mode is <code>CL_ADDRESS_NONE</code> and the selected texel location <code>(i,j,k)</code> refers to a location outside the image, the color value for the texel is undefined.</p>
</div>
</div>
<div class="sect4">
<h5 id="clamp-linear-filtering">Linear Filtering</h5>
<div class="paragraph">
<p>When the filter mode is <code>CL_FILTER_LINEAR</code>, a 2 x 2 square of image elements (for a 2D image) or a 2 x 2 x 2 cube of image elements (for a 3D image is selected).
This 2 x 2 square or 2 x 2 x 2 cube is obtained as follows.</p>
</div>
<div class="paragraph">
<p>Let:</p>
</div>
<div class="stemblock">
<div class="content">
\[\begin{aligned}
i0 &amp; = address\_mode((int)floor(u - 0.5))\\
j0 &amp; = address\_mode((int)floor(v - 0.5))\\
k0 &amp; = address\_mode((int)floor(w - 0.5))\\
i1 &amp; = address\_mode((int)floor(u - 0.5) + 1)\\
j1 &amp; = address\_mode((int)floor(v - 0.5) + 1)\\
k1 &amp; = address\_mode((int)floor(w - 0.5) + 1)\\
a &amp; = frac(u - 0.5)\\
b &amp; = frac(v - 0.5)\\
c &amp; = frac(w - 0.5)
\end{aligned}\]
</div>
</div>
<div class="paragraph">
<p>The frac function determines the fractional part of x and is computed as:</p>
</div>
<div class="stemblock">
<div class="content">
\[\begin{aligned}
frac(x) &amp; = x - floor(x)
\end{aligned}\]
</div>
</div>
<div class="paragraph">
<p>For a 3D image, the color value is computed as:</p>
</div>
<div class="stemblock">
<div class="content">
\[\begin{array}{rcl}
T &amp;=&amp; (1 - a) \times (1 - b) \times (1 - c) \times T_{i0j0k0}\\
&amp; &amp; {} + a \times (1 - b) \times (1 - c) \times T_{i1j0k0}\\
&amp; &amp; {} + (1 - a) \times b \times (1 - c) \times T_{i0j1k0}\\
&amp; &amp; {} + a \times b \times (1 - c) \times T_{i1j1k0}\\
&amp; &amp; {} + (1 - a) \times (1 - b) \times c \times T_{i0j0k1}\\
&amp; &amp; {} + a \times (1 - b) \times c \times T_{i1j0k1}\\
&amp; &amp; {} + (1 - a) \times b \times c \times T_{i0j1k1}\\
&amp; &amp; {} + a \times b \times c \times T_{i1j1k1}
\end{array}\]
</div>
</div>
<div class="paragraph">
<p>where <code>T<sub>ijk</sub></code> is the image element at location <code>(i,j,k)</code> in the 3D image.</p>
</div>
<div class="paragraph">
<p>For a 2D image, the color value is computed as:</p>
</div>
<div class="stemblock">
<div class="content">
\[\begin{array}{rcl}
T &amp;=&amp; (1 - a) \times (1 - b) \times T_{i0j0}\\
&amp; &amp; {} + a \times (1 - b) \times T_{i1j0}\\
&amp; &amp; {} + (1 - a) \times b \times T_{i0j1}\\
&amp; &amp; {} + a \times b \times T_{i1j1}
\end{array}\]
</div>
</div>
<div class="paragraph">
<p>where <code>T<sub>ij</sub></code> is the image element at location <code>(i,j)</code> in the 2D image.</p>
</div>
<div class="paragraph">
<p>If the addressing mode is <code>CL_ADDRESS_CLAMP</code> or <code>CL_ADDRESS_CLAMP_TO_EDGE</code>, and any of the selected <code>T<sub>ijk</sub></code> or <code>T<sub>ij</sub></code> refers to a location outside the image, the border color is used as the image element.</p>
</div>
<div class="paragraph">
<p>Otherwise, if the addressing mode is <code>CL_ADDRESS_NONE</code>, and any of the selected <code>T<sub>ijk</sub></code> or <code>T<sub>ij</sub></code> refers to a location outside the image, the color value is undefined.</p>
</div>
<div class="paragraph">
<p>If the image channel type is <code>CL_FLOAT</code> or <code>CL_HALF_FLOAT</code>, and any of the image elements <code>T<sub>ijk</sub></code> or <code>T<sub>ij</sub></code> is INF or NaN, the color value is undefined.</p>
</div>
</div>
</div>
<div class="sect3">
<h4 id="repeat-addressing">7.2.2. Repeat Addressing Mode</h4>
<div class="paragraph">
<p>We now discuss how the addressing and filter modes are applied to generate the appropriate sample locations to read from the image if the addressing mode is <code>CL_ADDRESS_REPEAT</code>.</p>
</div>
<div class="sect4">
<h5 id="repeat-nearest-filtering">Nearest Filtering</h5>
<div class="paragraph">
<p>When filter mode is <code>CL_FILTER_NEAREST</code>, the result of the image read instruction is the image element that is nearest (in Manhattan distance) to the image element location <code>(i,j,k)</code>.
The image element location <code>(i,j,k)</code> is computed as:</p>
</div>
<div class="stemblock">
<div class="content">
\[\begin{array}{l}
u = (s - floor(s)) \times w_t\\
i = (int)floor(u)\\
if\ (i &gt; w_t - 1)\\
\qquad i = i - w_t\\
v = (t - floor(t)) \times h_t\\
j = (int)floor(v)\\
if\ (j &gt; h_t - 1)\\
\qquad j = j - h_t\\
w = (r - floor(r)) \times d_t\\
k = (int)floor(w)\\
if\ (k &gt; d_t - 1)\\
\qquad k = k - d_t
\end{array}\]
</div>
</div>
<div class="paragraph">
<p>For a 3D image, the image element at location (i, j, k) becomes the color value.
For a 2D image, the image element at location (i, j) becomes the color value.</p>
</div>
</div>
<div class="sect4">
<h5 id="repeat-linear-filtering">Linear Filtering</h5>
<div class="paragraph">
<p>When filter mode is <code>CL_FILTER_LINEAR</code>, a 2 x 2 square of image elements for a 2D image or a 2 x 2 x 2 cube of image elements for a 3D image is selected.
This 2 x 2 square or 2 x 2 x 2 cube is obtained as follows.</p>
</div>
<div class="paragraph">
<p>Let</p>
</div>
<div class="stemblock">
<div class="content">
\[\begin{array}{l}
u = (s - floor(s)) \times w_t\\
i0 = (int)floor(u - 0.5)\\
i1 = i0 + 1\\
if (i0 &lt; 0)\\
i0 = w_t + i0\\
if\ (i1 &gt; w_t - 1)\\
\qquad i1 = i1 - w_t\\
v = (t - floor(t)) \times h_t\\
j0 = (int)floor(v - 0.5)\\
j1 = j0 + 1\\
if (j0 &lt; 0)\\
j0 = h_t + j0\\
if\ (j1 &gt; h_t - 1)\\
\qquad j1 = j1 - h_t\\
w = (r - floor(r)) \times d_t\\
k0 = (int)floor(w - 0.5)\\
k1 = k0 + 1\\
if (k0 &lt; 0)\\
\qquad k0 = d_t + k0\\
if\ (k1 &gt; d_t - 1)\\
\qquad k1 = k1 - d_t\\
a = frac(u - 0.5)\\
b = frac(v - 0.5)\\
c = frac(w - 0.5)
\end{array}\]
</div>
</div>
<div class="paragraph">
<p>For a 3D image, the color value is computed as:</p>
</div>
<div class="stemblock">
<div class="content">
\[\begin{array}{rcl}
T &amp;=&amp; (1 - a) \times (1 - b) \times (1 - c) \times T_{i0j0k0}\\
&amp; &amp; {} + a \times (1 - b) \times (1 - c) \times T_{i1j0k0}\\
&amp; &amp; {} + (1 - a) \times b \times (1 - c) \times T_{i0j1k0}\\
&amp; &amp; {} + a \times b \times (1 - c) \times T_{i1j1k0}\\
&amp; &amp; {} + (1 - a) \times (1 - b) \times c \times T_{i0j0k1}\\
&amp; &amp; {} + a \times (1 - b) \times c \times T_{i1j0k1}\\
&amp; &amp; {} + (1 - a) \times b \times c \times T_{i0j1k1}\\
&amp; &amp; {} + a \times b \times c \times T_{i1j1k1}
\end{array}\]
</div>
</div>
<div class="paragraph">
<p>where <code>T<sub>ijk</sub></code> is the image element at location <code>(i,j,k)</code> in the 3D image.</p>
</div>
<div class="paragraph">
<p>For a 2D image, the color value is computed as:</p>
</div>
<div class="stemblock">
<div class="content">
\[\begin{array}{rcl}
T &amp;=&amp;(1 - a) \times (1 - b) \times T_{i0j0}\\
&amp; &amp; {} + a \times (1 - b) \times T_{i1j0}\\
&amp; &amp; {} + (1 - a) \times b \times T_{i0j1}\\
&amp; &amp; {} + a \times b \times T_{i1j1}
\end{array}\]
</div>
</div>
<div class="paragraph">
<p>where <code>T<sub>ij</sub></code> is the image element at location <code>(i,j)</code> in the 2D image.</p>
</div>
<div class="paragraph">
<p>If the image channel type is <code>CL_FLOAT</code> or <code>CL_HALF_FLOAT</code>, and any of the image elements <code>T<sub>ijk</sub></code> or <code>T<sub>ij</sub></code> is INF or NaN, the color value is undefined.</p>
</div>
</div>
</div>
<div class="sect3">
<h4 id="mirrored-repeat-addressing">7.2.3. Mirrored Repeat Addressing Mode</h4>
<div class="paragraph">
<p>We now discuss how the addressing and filter modes are applied to generate the appropriate sample locations to read from the image if the addressing mode is <code>CL_ADDRESS_MIRRORED_REPEAT</code>.
The <code>CL_ADDRESS_MIRRORED_REPEAT</code> addressing mode causes the image to be read as if it is tiled at every integer seam, with the interpretation of the image data flipped at each integer crossing.</p>
</div>
<div class="sect4">
<h5 id="mirrored-repeat-nearest-filtering">Nearest Filtering</h5>
<div class="paragraph">
<p>When filter mode is <code>CL_FILTER_NEAREST</code>, the result of the image read instruction is the image element that is nearest (in Manhattan distance) to the image element location <code>(i,j,k)</code>.
The image element location <code>(i,j,k)</code> is computed as:</p>
</div>
<div class="stemblock">
<div class="content">
\[\begin{array}{rcl}
s' &amp;=&amp; 2.0f \times rint(0.5f \times s)\\
s` &amp;=&amp; fabs(s - s`)\\
u &amp;=&amp; s' \times w_t\\
i &amp;=&amp; (int)floor(u)\\
i &amp;=&amp; min(i, w_t - 1)\\
t' &amp;=&amp; 2.0f \times rint(0.5f \times t)\\
t` &amp;=&amp; fabs(t - t`)\\
v &amp;=&amp; t' \times h_t\\
j &amp;=&amp; (int)floor(v)\\
j &amp;=&amp; min(j, h_t - 1)\\
r' &amp;=&amp; 2.0f \times rint(0.5f \times r)\\
r` &amp;=&amp; fabs(r - r`)\\
w &amp;=&amp; r' \times d_t\\
k &amp;=&amp; (int)floor(w)\\
k &amp;=&amp; min(k, d_t - 1)
\end{array}\]
</div>
</div>
<div class="paragraph">
<p>For a 3D image, the image element at location (i, j, k) becomes the color value.
For a 2D image, the image element at location (i, j) becomes the color value.</p>
</div>
</div>
<div class="sect4">
<h5 id="mirrored-repeat-linear-filtering">Linear Filtering</h5>
<div class="paragraph">
<p>When filter mode is <code>CL_FILTER_LINEAR</code>, a 2 x 2 square of image elements for a 2D image or a 2 x 2 x 2 cube of image elements for a 3D image is selected.
This 2 x 2 square or 2 x 2 x 2 cube is obtained as follows.</p>
</div>
<div class="paragraph">
<p>Let</p>
</div>
<div class="stemblock">
<div class="content">
\[\begin{array}{rcl}
s' &amp;=&amp; 2.0f \times rint(0.5f \times s)\\
s` &amp;=&amp; fabs(s - s`)\\
u &amp;=&amp; s' \times w_t\\
i0 &amp;=&amp; (int)floor(u - 0.5f)\\
i1 &amp;=&amp; i0 + 1\\
i0 &amp;=&amp; max(i0, 0)\\
i1 &amp;=&amp; min(i1, w_t - 1)\\
t' &amp;=&amp; 2.0f \times rint(0.5f \times t)\\
t` &amp;=&amp; fabs(t - t`)\\
v &amp;=&amp; t' \times h_t\\
j0 &amp;=&amp; (int)floor(v - 0.5f)\\
j1 &amp;=&amp; j0 + 1\\
j0 &amp;=&amp; max(j0, 0)\\
j1 &amp;=&amp; min(j1, h_t - 1)\\
r' &amp;=&amp; 2.0f \times rint(0.5f \times r)\\
r` &amp;=&amp; fabs(r - r`)\\
w &amp;=&amp; r' \times d_t\\
k0 &amp;=&amp; (int)floor(w - 0.5f)\\
k1 &amp;=&amp; k0 + 1\\
k0 &amp;=&amp; max(k0, 0)\\
k1 &amp;=&amp; min(k1, d_t - 1)\\
a &amp;=&amp; frac(u - 0.5)\\
b &amp;=&amp; frac(v - 0.5)\\
c &amp;=&amp; frac(w - 0.5)
\end{array}\]
</div>
</div>
<div class="paragraph">
<p>For a 3D image, the color value is computed as:</p>
</div>
<div class="stemblock">
<div class="content">
\[\begin{array}{rcl}
T &amp;=&amp; (1 - a) \times (1 - b) \times (1 - c) \times T_{i0j0k0}\\
&amp; &amp; {} + a \times (1 - b) \times (1 - c) \times T_{i1j0k0}\\
&amp; &amp; {} + (1 - a) \times b \times (1 - c) \times T_{i0j1k0}\\
&amp; &amp; {} + a \times b \times (1 - c) \times T_{i1j1k0}\\
&amp; &amp; {} + (1 - a) \times (1 - b) \times c \times T_{i0j0k1}\\
&amp; &amp; {} + a \times (1 - b) \times c \times T_{i1j0k1}\\
&amp; &amp; {} + (1 - a) \times b \times c \times T_{i0j1k1}\\
&amp; &amp; {} + a \times b \times c \times T_{i1j1k1}
\end{array}\]
</div>
</div>
<div class="paragraph">
<p>where <code>T<sub>ijk</sub></code> is the image element at location <code>(i,j,k)</code> in the 3D image.</p>
</div>
<div class="paragraph">
<p>For a 2D image, the color value is computed as:</p>
</div>
<div class="stemblock">
<div class="content">
\[\begin{array}{rcl}
T &amp;=&amp; (1 - a) \times (1 - b) \times T_{i0j0}\\
&amp; &amp; {} + a \times (1 - b) \times T_{i1j0}\\
&amp; &amp; {} + (1 - a) \times b \times T_{i0j1}\\
&amp; &amp; {} + a \times b \times T_{i1j1}
\end{array}\]
</div>
</div>
<div class="paragraph">
<p>where <code>T<sub>ij</sub></code> is the image element at location <code>(i,j)</code> in the 2D image.</p>
</div>
<div class="paragraph">
<p>For a 1D image, the color value is computed as:</p>
</div>
<div class="stemblock">
<div class="content">
\[\begin{array}{rcl}
T &amp;=&amp; (1 - a) \times T_i0 + a \times T_i1
\end{array}\]
</div>
</div>
<div class="paragraph">
<p>where <code>T<sub>i</sub></code> is the image element at location <code>(i)</code> in the 1D image.</p>
</div>
<div class="paragraph">
<p>If the image channel type is <code>CL_FLOAT</code> or <code>CL_HALF_FLOAT</code> and any of the image elements <code>T<sub>ijk</sub></code> or <code>T<sub>ij</sub></code> is INF or NaN, the color value is undefined.</p>
</div>
</div>
</div>
</div>
<div class="sect2">
<h3 id="precision-of-addressing-and-filter-modes">7.3. Precision of Addressing and Filter Modes</h3>
<div class="paragraph">
<p>If the sampler is specified as using unnormalized coordinates (floating-point or integer coordinates), filter mode set to <code>CL_FILTER_NEAREST</code> and addressing mode set to one of the following modes - <code>CL_ADDRESS_CLAMP</code>, <code>CL_ADDRESS_CLAMP_TO_EDGE</code> or <code>CL_ADDRESS_NONE</code> - the location of the image element in the image given by <code>(i,j,k)</code> will be computed without any loss of precision.</p>
</div>
<div class="paragraph">
<p>For all other sampler combinations of normalized or unnormalized coordinates, filter modes, and addressing modes, the relative error or precision of the addressing mode calculations and the image filter operation are not defined.
To ensure precision of image addressing and filter calculations across any OpenCL device for these sampler combinations, developers may unnormalize the image coordinate in the kernel, and then implement the linear filter in the kernel with appropriate read image instructions with a sampler that uses unnormalized coordinates, filter mode set to <code>CL_FILTER_NEAREST</code>, addressing mode set to <code>CL_ADDRESS_CLAMP</code>, <code>CL_ADDRESS_CLAMP_TO_EDGE</code> or <code>CL_ADDRESS_NONE</code>, and finally performing the interpolation of color values read from the image to generate the filtered color value.</p>
</div>
</div>
<div class="sect2">
<h3 id="conversion-rules">7.4. Conversion Rules</h3>
<div class="paragraph">
<p>In this section we discuss conversion rules that are applied when reading and writing images in a kernel.</p>
</div>
<div class="sect3">
<h4 id="conversion-rules-for-normalized-integer-channel-data-types">7.4.1. Conversion Rules for Normalized Integer Channel Data Types</h4>
<div class="paragraph">
<p>In this section we discuss converting normalized integer channel data types to half-precision and single-precision floating-point values and vice-versa.</p>
</div>
<div class="sect4">
<h5 id="converting-normalized-integer-channel-data-types-to-half-precision-floating-point-values">Converting Normalized Integer Channel Data Types to Half Precision Floating-point Values</h5>
<div class="paragraph">
<p>For images created with image channel data type of <code>CL_UNORM_INT8</code> and <code>CL_UNORM_INT16</code>, image read instructions will convert the channel values from an 8-bit or 16-bit unsigned integer to normalized half precision floating-point values in the range [0.0h &#8230;&#8203; 1.0h].</p>
</div>
<div class="paragraph">
<p>For images created with image channel data type of <code>CL_SNORM_INT8</code> and <code>CL_SNORM_INT16</code>, image read instructions will convert the channel values from an 8-bit or 16-bit signed integer to normalized half precision floating-point values in the range [-1.0h &#8230;&#8203; 1.0h].</p>
</div>
<div class="paragraph">
<p>These conversions are performed as follows:</p>
</div>
<div class="ulist">
<ul>
<li>
<p><code>CL_UNORM_INT8</code> (8-bit unsigned integer) &#8594; <code>half</code></p>
<div class="stemblock">
<div class="content">
\[normalized\_half\_value(x)=round\_to\_half(\frac{x}{255})\]
</div>
</div>
</li>
<li>
<p><code>CL_UNORM_INT_101010</code> (10-bit unsigned integer) &#8594; <code>half</code></p>
<div class="stemblock">
<div class="content">
\[normalized\_half\_value(x)=round\_to\_half(\frac{x}{1023})\]
</div>
</div>
</li>
<li>
<p><code>CL_UNORM_INT16</code> (16-bit unsigned integer) &#8594; <code>half</code></p>
<div class="stemblock">
<div class="content">
\[normalized\_half\_value(x)=round\_to\_half(\frac{x}{65535})\]
</div>
</div>
</li>
<li>
<p><code>CL_SNORM_INT8</code> (8-bit signed integer) &#8594; <code>half</code></p>
<div class="stemblock">
<div class="content">
\[normalized\_half\_value(x)=max(-1.0h, round\_to\_half(\frac{x}{127}))\]
</div>
</div>
</li>
<li>
<p><code>CL_SNORM_INT16</code> (16-bit signed integer) &#8594; <code>half</code></p>
<div class="stemblock">
<div class="content">
\[normalized\_half\_value(x)=max(-1.0h, round\_to\_half(\frac{x}{32767}))\]
</div>
</div>
</li>
</ul>
</div>
<div class="paragraph">
<p>The precision of the above conversions is &lt;= 1.5 ulp except for the following cases:</p>
</div>
<div class="paragraph">
<p>For <code>CL_UNORM_INT8</code>:</p>
</div>
<div class="ulist">
<ul>
<li>
<p>0 must convert to 0.0h, and</p>
</li>
<li>
<p>255 must convert to 1.0h</p>
</li>
</ul>
</div>
<div class="paragraph">
<p>For <code>CL_UNORM_INT_101010</code>:</p>
</div>
<div class="ulist">
<ul>
<li>
<p>0 must convert to 0.0h, and</p>
</li>
<li>
<p>1023 must convert to 1.0h</p>
</li>
</ul>
</div>
<div class="paragraph">
<p>For <code>CL_UNORM_INT16</code>:</p>
</div>
<div class="ulist">
<ul>
<li>
<p>0 must convert to 0.0h, and</p>
</li>
<li>
<p>65535 must convert to 1.0h</p>
</li>
</ul>
</div>
<div class="paragraph">
<p>For <code>CL_SNORM_INT8</code>:</p>
</div>
<div class="ulist">
<ul>
<li>
<p>-128 and -127 must convert to -1.0h,</p>
</li>
<li>
<p>0 must convert to 0.0h, and</p>
</li>
<li>
<p>127 must convert to 1.0h</p>
</li>
</ul>
</div>
<div class="paragraph">
<p>For <code>CL_SNORM_INT16</code>:</p>
</div>
<div class="ulist">
<ul>
<li>
<p>-32768 and -32767 must convert to -1.0h,</p>
</li>
<li>
<p>0 must convert to 0.0h, and</p>
</li>
<li>
<p>32767 must convert to 1.0h</p>
</li>
</ul>
</div>
</div>
<div class="sect4">
<h5 id="converting-half-precision-floating-point-values-to-normalized-integer-channel-data-types">Converting Half Precision Floating-point Values to Normalized Integer Channel Data Types</h5>
<div class="paragraph">
<p>For images created with image channel data type of <code>CL_UNORM_INT8</code> and <code>CL_UNORM_INT16</code>, image write instructions will convert the half precision floating-point color value to an 8-bit or 16-bit unsigned integer.</p>
</div>
<div class="paragraph">
<p>For images created with image channel data type of <code>CL_SNORM_INT8</code> and <code>CL_SNORM_INT16</code>, image write instructions will convert the half precision floating-point color value to an 8-bit or 16-bit signed integer.</p>
</div>
<div class="paragraph">
<p>OpenCL implementations may choose to approximate the rounding mode used in the conversions described below.
When approximate rounding is used instead of the preferred rounding, the result of the conversion must satisfy the bound given below.</p>
</div>
<div class="paragraph">
<p>The conversions from half precision floating-point values to normalized integer values are performed is as follows:</p>
</div>
<div class="ulist">
<ul>
<li>
<p><code>half</code> &#8594; <code>CL_UNORM_INT8</code> (8-bit unsigned integer)</p>
<div class="stemblock">
<div class="content">
\[\begin{aligned}
&amp; f(x)=max(0,min(255,255 \times x))\\
\\
&amp; f_{preferred}(x) =
\begin{cases}
round\_to\_nearest\_even\_uint8(f(x)) &amp; x \neq \infty \text{ and } x \neq NaN\\
\text{implementation-defined} &amp; x = \infty \text{ or } x = NaN
\end{cases}\\
&amp; f_{approx}(x) =
\begin{cases}
round\_to\_impl\_uint8(f(x)) &amp; x \neq \infty \text{ and } x \neq NaN\\
\text{implementation-defined} &amp; x = \infty \text{ or } x = NaN
\end{cases}\\
\\
&amp; |f(x) - f_{approx}(x)|\leq 0.6, x \neq \infty \text{ and } x \neq NaN
\end{aligned}\]
</div>
</div>
</li>
<li>
<p><code>half</code> &#8594; <code>CL_UNORM_INT16</code> (16-bit unsigned integer)</p>
<div class="stemblock">
<div class="content">
\[\begin{aligned}
&amp; f(x)=max(0,min(65535,65535 \times x))\\
\\
&amp; f_{preferred}(x) =
\begin{cases}
round\_to\_nearest\_even\_uint16(f(x)) &amp; \quad x \neq \infty \text{ and } x \neq NaN\\
\text{implementation-defined} &amp; \quad x = \infty \text{ or } x = NaN
\end{cases}\\
&amp; f_{approx}(x) =
\begin{cases}
round\_to\_impl\_uint16(f(x)) &amp; \quad x \neq \infty \text{ and } x \neq NaN\\
\text{implementation-defined} &amp; \quad x = \infty \text{ or } x = NaN
\end{cases}\\
\\
&amp; |f(x) - f_{approx}(x)|\leq 0.6, x \neq \infty \text{ and } x \neq NaN
\end{aligned}\]
</div>
</div>
</li>
<li>
<p><code>half</code> &#8594; <code>CL_SNORM_INT8</code> (8-bit signed integer)</p>
<div class="stemblock">
<div class="content">
\[\begin{aligned}
&amp; f(x)=max(-128,min(127,127 \times x))\\
\\
&amp; f_{preferred}(x) =
\begin{cases}
round\_to\_nearest\_even\_int8(f(x)) &amp; \quad x \neq \infty \text{ and } x \neq NaN\\
\text{implementation-defined} &amp; \quad x = \infty \text{ or } x = NaN
\end{cases}\\
&amp; f_{approx}(x) =
\begin{cases}
round\_to\_impl\_int8(f(x)) &amp; \quad x \neq \infty \text{ and } x \neq NaN\\
\text{implementation-defined} &amp; \quad x = \infty \text{ or } x = NaN
\end{cases}\\
\\
&amp; |f(x) - f_{approx}(x)|\leq 0.6, x \neq \infty \text{ and } x \neq NaN
\end{aligned}\]
</div>
</div>
</li>
<li>
<p><code>half</code> &#8594; <code>CL_SNORM_INT16</code> (16-bit signed integer)</p>
<div class="stemblock">
<div class="content">
\[\begin{aligned}
&amp; f(x)=max(-32768,min(32767,32767 \times x))\\
\\
&amp; f_{preferred}(x) =
\begin{cases}
round\_to\_nearest\_even\_int16(f(x)) &amp; \quad x \neq \infty \text{ and } x \neq NaN\\
\text{implementation-defined} &amp; \quad x = \infty \text{ or } x = NaN
\end{cases}\\
&amp; f_{approx}(x) =
\begin{cases}
round\_to\_impl\_int16(f(x)) &amp; \quad x \neq \infty \text{ and } x \neq NaN\\
\text{implementation-defined} &amp; \quad x = \infty \text{ or } x = NaN
\end{cases}\\
\\
&amp; |f(x) - f_{approx}(x)|\leq 0.6, x \neq \infty \text{ and } x \neq NaN
\end{aligned}\]
</div>
</div>
</li>
</ul>
</div>
</div>
<div class="sect4">
<h5 id="converting-normalized-integer-channel-data-types-to-floating-point-values">Converting Normalized Integer Channel Data Types to Floating-point Values</h5>
<div class="paragraph">
<p>For images created with image channel data type of <code>CL_UNORM_INT8</code> and <code>CL_UNORM_INT16</code>, image read instructions will convert the channel values from an 8-bit or 16-bit unsigned integer to normalized floating-point values in the range [0.0f &#8230;&#8203; 1.0f].</p>
</div>
<div class="paragraph">
<p>For images created with image channel data type of <code>CL_SNORM_INT8</code> and <code>CL_SNORM_INT16</code>, image read instructions will convert the channel values from an 8-bit or 16-bit signed integer to normalized floating-point values in the range [-1.0f &#8230;&#8203; 1.0f].</p>
</div>
<div class="paragraph">
<p>These conversions are performed as follows:</p>
</div>
<div class="ulist">
<ul>
<li>
<p><code>CL_UNORM_INT8</code> (8-bit unsigned integer) &#8594; <code>float</code></p>
<div class="stemblock">
<div class="content">
\[normalized\_float\_value(x)=round\_to\_float(\frac{x}{255})\]
</div>
</div>
</li>
<li>
<p><code>CL_UNORM_INT_101010</code> (10-bit unsigned integer) &#8594; <code>float</code></p>
<div class="stemblock">
<div class="content">
\[normalized\_float\_value(x)=round\_to\_float(\frac{x}{1023})\]
</div>
</div>
</li>
<li>
<p><code>CL_UNORM_INT16</code> (16-bit unsigned integer) &#8594; <code>float</code></p>
<div class="stemblock">
<div class="content">
\[normalized\_float\_value(x)=round\_to\_float(\frac{x}{65535})\]
</div>
</div>
</li>
<li>
<p><code>CL_SNORM_INT8</code> (8-bit signed integer) &#8594; <code>float</code></p>
<div class="stemblock">
<div class="content">
\[normalized\_float\_value(x)=max(-1.0f, round\_to\_float(\frac{x}{127}))\]
</div>
</div>
</li>
<li>
<p><code>CL_SNORM_INT16</code> (16-bit signed integer) &#8594; <code>float</code></p>
<div class="stemblock">
<div class="content">
\[normalized\_float\_value(x)=max(-1.0f, round\_to\_float(\frac{x}{32767}))\]
</div>
</div>
</li>
</ul>
</div>
<div class="paragraph">
<p>The precision of the above conversions is &lt;= 1.5 ulp except for the following cases.</p>
</div>
<div class="paragraph">
<p>For <code>CL_UNORM_INT8</code>:</p>
</div>
<div class="ulist">
<ul>
<li>
<p>0 must convert to 0.0f, and</p>
</li>
<li>
<p>255 must convert to 1.0f</p>
</li>
</ul>
</div>
<div class="paragraph">
<p>For <code>CL_UNORM_INT_101010</code>:</p>
</div>
<div class="ulist">
<ul>
<li>
<p>0 must convert to 0.0f, and</p>
</li>
<li>
<p>1023 must convert to 1.0f</p>
</li>
</ul>
</div>
<div class="paragraph">
<p>For <code>CL_UNORM_INT16</code>:</p>
</div>
<div class="ulist">
<ul>
<li>
<p>0 must convert to 0.0f, and</p>
</li>
<li>
<p>65535 must convert to 1.0f</p>
</li>
</ul>
</div>
<div class="paragraph">
<p>For <code>CL_SNORM_INT8</code>:</p>
</div>
<div class="ulist">
<ul>
<li>
<p>-128 and -127 must convert to -1.0f,</p>
</li>
<li>
<p>0 must convert to 0.0f, and</p>
</li>
<li>
<p>127 must convert to 1.0f</p>
</li>
</ul>
</div>
<div class="paragraph">
<p>For <code>CL_SNORM_INT16</code>:</p>
</div>
<div class="ulist">
<ul>
<li>
<p>-32768 and -32767 must convert to -1.0f,</p>
</li>
<li>
<p>0 must convert to 0.0f, and</p>
</li>
<li>
<p>32767 must convert to 1.0f</p>
</li>
</ul>
</div>
</div>
<div class="sect4">
<h5 id="converting-floating-point-values-to-normalized-integer-channel-data-types">Converting Floating-point Values to Normalized Integer Channel Data Types</h5>
<div class="paragraph">
<p>For images created with image channel data type of <code>CL_UNORM_INT8</code> and <code>CL_UNORM_INT16</code>, image write instructions will convert the floating-point color value to an 8-bit or 16-bit unsigned integer.</p>
</div>
<div class="paragraph">
<p>For images created with image channel data type of <code>CL_SNORM_INT8</code> and <code>CL_SNORM_INT16</code>, image write instructions will convert the floating-point color value to an 8-bit or 16-bit signed integer.</p>
</div>
<div class="paragraph">
<p>OpenCL implementations may choose to approximate the rounding mode used in the conversions described below.
When approximate rounding is used instead of the preferred rounding, the result of the conversion must satisfy the bound given below.</p>
</div>
<div class="paragraph">
<p>The conversions from half precision floating-point values to normalized integer values are performed is as follows:</p>
</div>
<div class="ulist">
<ul>
<li>
<p><code>float</code> &#8594; <code>CL_UNORM_INT8</code> (8-bit unsigned integer)</p>
<div class="stemblock">
<div class="content">
\[\begin{aligned}
&amp; f(x)=max(0,min(255,255 \times x))\\
\\
&amp; f_{preferred}(x) =
\begin{cases}
round\_to\_nearest\_even\_uint8(f(x)) &amp; \quad x \neq \infty \text{ and } x \neq NaN\\
\text{implementation-defined} &amp; \quad x = \infty \text{ or } x = NaN
\end{cases}\\
&amp; f_{approx}(x) =
\begin{cases}
round\_to\_impl\_uint8(f(x)) &amp; \quad x \neq \infty \text{ and } x \neq NaN\\
\text{implementation-defined} &amp; \quad x = \infty \text{ or } x = NaN
\end{cases}\\
\\
&amp; |f(x) - f_{approx}(x)|\leq 0.6, x \neq \infty \text{ and } x \neq NaN
\end{aligned}\]
</div>
</div>
</li>
<li>
<p><code>float</code> &#8594; <code>CL_UNORM_INT_101010</code> (10-bit unsigned integer)</p>
<div class="stemblock">
<div class="content">
\[\begin{aligned}
&amp; f(x)=max(0,min(1023,1023 \times x))\\
\\
&amp; f_{preferred}(x) =
\begin{cases}
round\_to\_nearest\_even\_uint10(f(x)) &amp; \quad x \neq \infty \text{ and } x \neq NaN\\
\text{implementation-defined} &amp; \quad x = \infty \text{ or } x = NaN
\end{cases}\\
&amp; f_{approx}(x) =
\begin{cases}
round\_to\_impl\_uint10(f(x)) &amp; \quad x \neq \infty \text{ and } x \neq NaN\\
\text{implementation-defined} &amp; \quad x = \infty \text{ or } x = NaN
\end{cases}\\
\\
&amp; |f(x) - f_{approx}(x)|\leq 0.6, x \neq \infty \text{ and } x \neq NaN
\end{aligned}\]
</div>
</div>
</li>
<li>
<p><code>float</code> &#8594; <code>CL_UNORM_INT16</code> (16-bit unsigned integer)</p>
<div class="stemblock">
<div class="content">
\[\begin{aligned}
&amp; f(x)=max(0,min(65535,65535 \times x))\\
\\
&amp; f_{preferred}(x) =
\begin{cases}
round\_to\_nearest\_even\_uint16(f(x)) &amp; \quad x \neq \infty \text{ and } x \neq NaN\\
\text{implementation-defined} &amp; \quad x = \infty \text{ or } x = NaN
\end{cases}\\
&amp; f_{approx}(x) =
\begin{cases}
round\_to\_impl\_uint16(f(x)) &amp; \quad x \neq \infty \text{ and } x \neq NaN\\
\text{implementation-defined} &amp; \quad x = \infty \text{ or } x = NaN
\end{cases}\\
\\
&amp; |f(x) - f_{approx}(x)|\leq 0.6, x \neq \infty \text{ and } x \neq NaN
\end{aligned}\]
</div>
</div>
</li>
<li>
<p><code>float</code> &#8594; <code>CL_SNORM_INT8</code> (8-bit signed integer)</p>
<div class="stemblock">
<div class="content">
\[\begin{aligned}
&amp; f(x)=max(-128,min(127,127 \times x))\\
\\
&amp; f_{preferred}(x) =
\begin{cases}
round\_to\_nearest\_even\_uint8(f(x)) &amp; \quad x \neq \infty \text{ and } x \neq NaN\\
\text{implementation-defined} &amp; \quad x = \infty \text{ or } x = NaN
\end{cases}\\
&amp; f_{approx}(x) =
\begin{cases}
round\_to\_impl\_uint8(f(x)) &amp; \quad x \neq \infty \text{ and } x \neq NaN\\
\text{implementation-defined} &amp; \quad x = \infty \text{ or } x = NaN
\end{cases}\\
\\
&amp; |f(x) - f_{approx}(x)|\leq 0.6, x \neq \infty \text{ and } x \neq NaN
\end{aligned}\]
</div>
</div>
</li>
<li>
<p><code>float</code> &#8594; <code>CL_SNORM_INT16</code> (16-bit signed integer)</p>
<div class="stemblock">
<div class="content">
\[\begin{aligned}
&amp; f(x)=max(-32768,min(32767,32767 \times x))\\
\\
&amp; f_{preferred}(x) =
\begin{cases}
round\_to\_nearest\_even\_uint16(f(x)) &amp; \quad x \neq \infty \text{ and } x \neq NaN\\
\text{implementation-defined} &amp; \quad x = \infty \text{ or } x = NaN
\end{cases}\\
&amp; f_{approx}(x) =
\begin{cases}
round\_to\_impl\_uint16(f(x)) &amp; \quad x \neq \infty \text{ and } x \neq NaN\\
\text{implementation-defined} &amp; \quad x = \infty \text{ or } x = NaN
\end{cases}\\
\\
&amp; |f(x) - f_{approx}(x)|\leq 0.6, x \neq \infty \text{ and } x \neq NaN
\end{aligned}\]
</div>
</div>
</li>
</ul>
</div>
</div>
</div>
<div class="sect3">
<h4 id="conversion-rules-for-half-precision-floating-point-channel-data-type">7.4.2. Conversion Rules for Half Precision Floating-point Channel Data Type</h4>
<div class="paragraph">
<p>For images created with a channel data type of <code>CL_HALF_FLOAT</code>, the conversions of half to float and half to half are lossless.
Conversions from float to half round the mantissa using the round to nearest even or round to zero rounding mode.
Denormalized numbers for the half data type which may be generated when converting a float to a half may be flushed to zero.
A float NaN must be converted to an appropriate NaN in the half type.
A float INF must be converted to an appropriate INF in the half type.</p>
</div>
</div>
<div class="sect3">
<h4 id="conversion-rules-for-floating-point-channel-data-type">7.4.3. Conversion Rules for Floating-point Channel Data Type</h4>
<div class="paragraph">
<p>The following rules apply for reading and writing images created with channel data type of <code>CL_FLOAT</code>.</p>
</div>
<div class="ulist">
<ul>
<li>
<p>NaNs may be converted to a NaN value(s) supported by the device.</p>
</li>
<li>
<p>Denorms can be flushed to zero.</p>
</li>
<li>
<p>All other values must be preserved.</p>
</li>
</ul>
</div>
</div>
<div class="sect3">
<h4 id="conversion-rules-for-signed-and-unsigned-8-bit-16-bit-and-32-bit-integer-channel-data-types">7.4.4. Conversion Rules for Signed and Unsigned 8-bit, 16-bit and 32-bit Integer Channel Data Types</h4>
<div class="paragraph">
<p>For images created with image channel data type of <code>CL_SIGNED_INT8</code>, <code>CL_SIGNED_INT16</code> and <code>CL_SIGNED_INT32</code>, image read instructions will return the unmodified integer values stored in the image at specified location.</p>
</div>
<div class="paragraph">
<p>Likewise, for images created with image channel data type of <code>CL_UNSIGNED_INT8</code>, <code>CL_UNSIGNED_INT16</code> and <code>CL_UNSIGNED_INT32</code>, image read instructions will return the unmodified unsigned integer values stored in the image at specified location.</p>
</div>
<div class="paragraph">
<p>Image write instructions will perform one of the following conversions:</p>
</div>
<div class="ulist">
<ul>
<li>
<p>32 bit signed integer &#8594; <code>CL_SIGNED_INT8</code> (8-bit signed integer):</p>
<div class="stemblock">
<div class="content">
\[int8\_value(x) = clamp(x, -128, 127)\]
</div>
</div>
</li>
<li>
<p>32 bit signed integer &#8594; <code>CL_SIGNED_INT16</code> (16-bit signed integer):</p>
<div class="stemblock">
<div class="content">
\[int16\_value(x) = clamp(x, -32768, 32767)\]
</div>
</div>
</li>
<li>
<p>32 bit signed integer &#8594; <code>CL_SIGNED_INT32</code> (32-bit signed integer):</p>
<div class="stemblock">
<div class="content">
\[int32\_value(x) = x \quad \text{(no conversion)}\]
</div>
</div>
</li>
<li>
<p>32 bit unsigned integer &#8594; <code>CL_UNSIGNED_INT8</code> (8-bit unsigned integer):</p>
<div class="stemblock">
<div class="content">
\[uint8\_value(x) = clamp(x, 0, 255)\]
</div>
</div>
</li>
<li>
<p>32 bit unsigned integer &#8594; <code>CL_UNSIGNED_INT16</code> (16-bit unsigned integer):</p>
<div class="stemblock">
<div class="content">
\[uint16\_value(x) = clamp(x, 0, 65535)\]
</div>
</div>
</li>
<li>
<p>32 bit unsigned integer &#8594; <code>CL_UNSIGNED_INT32</code> (32-bit unsigned integer):</p>
<div class="stemblock">
<div class="content">
\[uint32\_value(x) = x \quad \text{(no conversion)}\]
</div>
</div>
</li>
</ul>
</div>
<div class="paragraph">
<p>The conversions described in this section must be correctly saturated.</p>
</div>
</div>
<div class="sect3">
<h4 id="conversion-rules-for-srgba-and-sbgra-images">7.4.5. Conversion Rules for sRGBA and sBGRA Images</h4>
<div class="paragraph">
<p>Standard RGB data, which roughly displays colors in a linear ramp of luminosity levels such that an average observer, under average viewing conditions, can view them as perceptually equal steps on an average display.
All 0s maps to 0.0f, and all 1s maps to 1.0f.
The sequence of unsigned integer encodings between all 0s and all 1s represent a nonlinear progression in the floating-point interpretation of the numbers between 0.0f to 1.0f.
For more detail, see the <a href="#sRGB-spec">SRGB color standard</a>.</p>
</div>
<div class="paragraph">
<p>Conversion from sRGB space is automatically done the image read instruction if the image channel order is one of the sRGB values described above.
When reading from an sRGB image, the conversion from sRGB to linear RGB is performed before filtering is applied.
If the format has an alpha channel, the alpha data is stored in linear color space.
Conversion to sRGB space is automatically done by the image write instruction if the image channel order is one of the sRGB values described above and the device supports writing to sRGB images.</p>
</div>
<div class="paragraph">
<p>If the format has an alpha channel, the alpha data is stored in linear color space.</p>
</div>
<div class="olist arabic">
<ol class="arabic">
<li>
<p>The following process is used by image read instructions to convert a normalized 8-bit unsigned integer sRGB color value x to a floating-point linear RGB color value y:</p>
<div class="olist loweralpha">
<ol class="loweralpha">
<li>
<p>Convert a normalized 8-bit unsigned integer sRGB value x to a floating-point sRGB value r as per rules described in <a href="#converting-normalized-integer-channel-data-types-to-floating-point-values">Converting Normalized Integer Channel Data Types to Floating-point Values</a> section.</p>
<div class="stemblock">
<div class="content">
\[r=normalized\_float\_value(x)\]
</div>
</div>
</li>
<li>
<p>Convert a floating-point sRGB value r to a floating-point linear RGB color value y:</p>
<div class="stemblock">
<div class="content">
\[\begin{aligned}
&amp; c_{linear}(x) =
\begin{cases}
\frac{r}{12.92} &amp; \quad r \geq 0 \text{ and } r \leq 0.04045\\
(\frac{r + 0.055}{1.055})^{2.4} &amp; \quad r &gt; 0.04045 \text{ and } \leq 1
\end{cases}\\
\\
&amp; y = c_{linear}(r)
\end{aligned}\]
</div>
</div>
</li>
</ol>
</div>
</li>
<li>
<p>The following process is used by image write instructions to convert a linear RGB floating-point color value y to a normalized 8-bit unsigned integer sRGB value x:</p>
<div class="olist loweralpha">
<ol class="loweralpha">
<li>
<p>Convert a floating-point linear RGB value y to a normalized floating point sRGB value r:</p>
<div class="stemblock">
<div class="content">
\[\begin{aligned}
&amp; c_{linear}(x) =
\begin{cases}
0 &amp; \quad y \geq NaN \text{ or } y &lt; 0\\
12.92 \times y &amp; \quad y \geq 0 \text{ and } y &lt; 0.0031308\\
1.055 \times y^{(\frac{1}{2.4})} &amp; \quad y \geq 0.0031308 \text{ and } y \leq 1\\
1 &amp; \quad y &gt; 1
\end{cases}\\
\\
&amp; r = c_{sRGB}(y)
\end{aligned}\]
</div>
</div>
</li>
<li>
<p>Convert a normalized floating-point sRGB value r to a normalized 8-bit unsigned integer sRGB value x as per rules described in <a href="#converting-floating-point-values-to-normalized-integer-channel-data-types">Converting Floating-point Values to Normalized Integer Channel Data Types</a> section.</p>
<div class="stemblock">
<div class="content">
\[\begin{aligned}
&amp; g(r) =
\begin{cases}
f_{preferred}(r) &amp; \quad \text{if rounding mode is round to even}\\
f_{approx}(r) &amp; \quad \text{if implementation-defined rounding mode}
\end{cases}\\
\\
&amp; x = g(r)
\end{aligned}\]
</div>
</div>
</li>
</ol>
</div>
</li>
</ol>
</div>
<div class="paragraph">
<p>The accuracy required when converting a normalized 8-bit unsigned integer sRGB color value x to a floating-point linear RGB color value y is given by:</p>
</div>
<div class="stemblock">
<div class="content">
\[|x-255 \times c_{sRGB}(y)|\leq 0.5\]
</div>
</div>
<div class="paragraph">
<p>The accuracy required when converting a linear RGB floating-point color value y to a normalized 8-bit unsigned integer sRGB value x is given by:</p>
</div>
<div class="stemblock">
<div class="content">
\[|x-255 \times c_{sRGB}(y)|\leq 0.6\]
</div>
</div>
</div>
</div>
<div class="sect2">
<h3 id="selecting-an-image-from-an-image-array">7.5. Selecting an Image from an Image Array</h3>
<div class="paragraph">
<p>Let <code>(u,v,w)</code> represent the unnormalized image coordinate values for reading from and/or writing to a 2D image in a 2D image array.</p>
</div>
<div class="paragraph">
<p>When read using a sampler, the 2D image layer selected is computed as:</p>
</div>
<div class="stemblock">
<div class="content">
\[layer = clamp(rint(w), 0, d_t - 1)\]
</div>
</div>
<div class="paragraph">
<p>otherwise the layer selected is computed as:</p>
</div>
<div class="stemblock">
<div class="content">
\[layer = w\]
</div>
</div>
<div class="paragraph">
<p>(since w is already an integer) and the result is undefined if w is not one of the integers 0, 1, &#8230;&#8203; <code>d<sub>t</sub></code> - 1.</p>
</div>
<div class="paragraph">
<p>Let <code>(u,v)</code> represent the unnormalized image coordinate values for reading from and/or writing to a 1D image in a 1D image array.</p>
</div>
<div class="paragraph">
<p>When read using a sampler, the 1D image layer selected is computed as:</p>
</div>
<div class="stemblock">
<div class="content">
\[layer = clamp(rint(v), 0, h_t - 1)\]
</div>
</div>
<div class="paragraph">
<p>otherwise the layer selected is computed as:</p>
</div>
<div class="stemblock">
<div class="content">
\[layer = v\]
</div>
</div>
<div class="paragraph">
<p>(since v is already an integer) and the result is undefined if v is not one of the integers 0, 1, &#8230;&#8203; <code>h<sub>t</sub></code> - 1.</p>
</div>
</div>
<div class="sect2">
<h3 id="_data_format_for_reading_and_writing_images">7.6. Data Format for Reading and Writing Images</h3>
<div class="paragraph">
<p>This section describes how image element data is returned by an
image read instruction or passed as the <em>Texel</em> data that is
written by an image write instruction:</p>
</div>
<div class="paragraph">
<p>For the following image channel orders, the data is a four
component vector type:</p>
</div>
<table class="tableblock frame-all grid-all stretch">
<caption class="title">Table 9. <em>Mapping Image Data to Vector Components</em></caption>
<colgroup>
<col style="width: 50%;">
<col style="width: 50%;">
</colgroup>
<thead>
<tr>
<th class="tableblock halign-left valign-top"><strong>Image Channel Order</strong></th>
<th class="tableblock halign-left valign-top"><strong>Components</strong></th>
</tr>
</thead>
<tbody>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>R</code>, <code>Rx</code></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">(R, 0, 0, 1)</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>A</code></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">(0, 0, 0, A)</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>RG</code>, <code>RGx</code></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">(R, G, 0, 1)</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>RGB</code>, <code>RGBx</code>, <code>sRGB</code>, <code>sRGBx</code></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">(R, G, B, 1)</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>RGBA</code>, <code>BGRA</code>, <code>ARGB</code>, <code>ABGR</code>, <code>sRGBA</code>, <code>sBGRA</code></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">(R, G, B, A)</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>Intensity</code></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">(I, I, I, I)</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>Luminance</code></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">(L, L, L, 1)</p></td>
</tr>
</tbody>
</table>
<div class="paragraph">
<p>For the following image channel orders, the data is a scalar type:</p>
</div>
<table class="tableblock frame-all grid-all stretch">
<caption class="title">Table 10. <em>Scalar Image Data</em></caption>
<colgroup>
<col style="width: 50%;">
<col style="width: 50%;">
</colgroup>
<thead>
<tr>
<th class="tableblock halign-left valign-top"><strong>Image Channel Order</strong></th>
<th class="tableblock halign-left valign-top"><strong>Scalar Value</strong></th>
</tr>
</thead>
<tbody>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>Depth</code></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">D</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>DepthStencil</code></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">D</p></td>
</tr>
</tbody>
</table>
<div class="paragraph">
<p>The following table describes the mapping from image channel data type
to the data vector component type or scalar type:</p>
</div>
<table class="tableblock frame-all grid-all stretch">
<caption class="title">Table 11. <em>Image Data Types</em></caption>
<colgroup>
<col style="width: 50%;">
<col style="width: 50%;">
</colgroup>
<thead>
<tr>
<th class="tableblock halign-left valign-top"><strong>Image Channel Order</strong></th>
<th class="tableblock halign-left valign-top"><strong>Data Type</strong></th>
</tr>
</thead>
<tbody>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>SnormInt8</code>,
<code>SnormInt16</code>,<br>
<code>UnormInt8</code>,
<code>UnormInt16</code>,<br>
<code>UnormShort565</code>,
<code>UnormShort555</code>,<br>
<code>UnormInt101010</code>,
<code>UnormInt101010_2</code>,<br>
<code>UnormInt24</code>,<br>
<code>HalfFloat</code>,<br>
<code>Float</code></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpTypeFloat</strong>, with <em>Width</em> equal to 16 or 32.</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><code>SignedInt8</code>,
<code>SignedInt16</code>,
<code>SignedInt32</code>,<br>
<code>UnsignedInt8</code>,
<code>UnsignedInt16</code>,
<code>UnsignedInt32</code></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>OpTypeInt</strong>, with <em>Width</em> equal to 32.</p></td>
</tr>
</tbody>
</table>
</div>
<div class="sect2">
<h3 id="_sampled_and_sampler_less_reads">7.7. Sampled and Sampler-less Reads</h3>
<div class="paragraph">
<p>SPIR-V instructions that read from an image without a sampler (such as <strong>OpImageRead</strong>) behave exactly the same as the corresponding image read instruction with a sampler that has <em>Sampler Filter Mode</em> set to <strong>Nearest</strong>, <strong>Non-Normalized</strong> coordinates, and <em>Sampler Addressing Mode</em> set to <strong>None</strong>.</p>
</div>
<div class="paragraph">
<p>There is one exception for cases where the image being read has <em>Image Format</em> equal to a floating-point type (such as <strong>R32f</strong>).
In this exceptional case, when channel data values are denormalized, the non-sampler image read instruction may return the denormalized data, while the sampler image read instruction may flush denormalized channel data values to zero.
The coordinates must be between 0 and image size in that dimension, non inclusive.</p>
</div>
</div>
</div>
</div>
<div class="sect1">
<h2 id="references">8. Normative References</h2>
<div class="sectionbody">
<div class="olist arabic">
<ol class="arabic">
<li>
<p><a id="ieee-754-spec"></a><em>IEEE Standard for Floating-Point Arithmetic</em>, IEEE Std 754-2008,
<a href="http://dx.doi.org/10.1109/IEEESTD.2008.4610935" class="bare">http://dx.doi.org/10.1109/IEEESTD.2008.4610935</a> , August, 2008.</p>
</li>
<li>
<p><a id="C99-spec"></a> &#8220;ISO/IEC 9899:1999 - Programming Languages - C&#8221;, with
technical corrigenda TC1 and TC2,
<a href="https://www.iso.org/standard/29237.html" class="bare">https://www.iso.org/standard/29237.html</a> .</p>
</li>
<li>
<p><a id="cpp14-spec"></a> &#8220;ISO/IEC 14882:2014 - Information technology - Programming
languages - C++&#8221;, <a href="https://www.iso.org/standard/64029.html" class="bare">https://www.iso.org/standard/64029.html</a> .</p>
</li>
<li>
<p><a id="opencl-spec"></a> &#8220;The OpenCL Specification, Version 3.0, Unified&#8221;,
<a href="https://www.khronos.org/registry/OpenCL/" class="bare">https://www.khronos.org/registry/OpenCL/</a> .</p>
</li>
<li>
<p><a id="opencl-c-spec"></a> &#8220;The OpenCL C Specification, Version 3.0&#8221;,
<a href="https://www.khronos.org/registry/OpenCL/" class="bare">https://www.khronos.org/registry/OpenCL/</a> .</p>
</li>
<li>
<p><a id="opencl-cpp-spec"></a> &#8220;The OpenCL C++ 1.0 Specification&#8221;,
<a href="https://www.khronos.org/registry/OpenCL/" class="bare">https://www.khronos.org/registry/OpenCL/</a> .</p>
</li>
<li>
<p><a id="opencl-extension-spec"></a> &#8220;The OpenCL Extension Specification, Version
3.0, Unified&#8221;, <a href="https://www.khronos.org/registry/OpenCL/" class="bare">https://www.khronos.org/registry/OpenCL/</a> .</p>
</li>
<li>
<p><a id="spirv-spec"></a> &#8220;SPIR-V Specification, Version 1.5, Unified&#8221;,
<a href="https://www.khronos.org/registry/spir-v/" class="bare">https://www.khronos.org/registry/spir-v/</a> .</p>
</li>
<li>
<p><a id="opencl-extended-instruction-set"></a> &#8220;OpenCL Extended Instruction Set
Specification&#8221;, <a href="https://www.khronos.org/registry/spir-v/" class="bare">https://www.khronos.org/registry/spir-v/</a> .</p>
</li>
<li>
<p><a id="ulp-definition"></a> Jean-Michel Muller. <em>On the definition of ulp(x)</em>.
RR-5504, INRIA. 2005, pp.16. &lt;inria-00070503&gt;
Currently hosted at
<a href="https://hal.inria.fr/inria-00070503/document">https://hal.inria.fr/inria-00070503/document</a>.</p>
</li>
<li>
<p><a id="sRGB-spec"></a> &#8220;IEC 61966-2-1:1999 Multimedia systems and equipment -
Colour measurement and management - Part 2-1: Colour management -
Default RGB colour space - sRGB&#8221;,
<a href="https://webstore.iec.ch/publication/6169" class="bare">https://webstore.iec.ch/publication/6169</a> .</p>
</li>
</ol>
</div>
</div>
</div>
</div>
<div id="footnotes">
<hr>
<div class="footnote" id="_footnotedef_1">
<a href="#_footnoteref_1">1</a>. Here <code>TYPE_MIN</code> and <code>TYPE_MIN_EXP</code> should be substituted by constants appropriate to the floating-point type under consideration, such as <code>FLT_MIN</code> and <code>FLT_MIN_EXP</code> for float.
</div>
</div>
<div id="footer">
<div id="footer-text">
Version v3.0.1-Provisional<br>
Last updated 2020-04-26 21:05:33 -0700
</div>
</div>
<script src="https://cdnjs.cloudflare.com/ajax/libs/mathjax/2.7.4/MathJax.js?config=TeX-MML-AM_HTMLorMML"></script>
</body>
</html>