summaryrefslogtreecommitdiff
path: root/style/extensions.adoc
blob: c3fc78d2a0e9ea3cf89a595283b0ba47dfa2133a (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
463
464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
479
480
481
482
483
484
485
486
487
488
489
490
491
492
493
494
495
496
497
498
499
500
501
502
503
504
505
506
507
508
509
510
511
512
513
514
515
516
517
518
519
520
521
522
523
524
525
526
527
528
529
530
531
532
533
534
535
536
537
538
539
540
541
542
543
544
545
546
547
548
549
550
551
552
553
554
555
556
557
558
559
560
561
562
563
564
565
566
567
568
569
570
571
572
573
574
575
576
577
578
579
580
581
582
583
584
585
586
587
588
589
590
591
592
593
594
595
596
597
598
599
600
601
602
603
604
605
606
607
608
609
610
611
612
613
614
615
616
617
618
619
620
621
622
623
624
625
626
627
628
629
630
631
632
633
634
635
636
637
638
639
640
641
642
643
644
645
646
647
648
649
650
651
652
653
654
655
656
657
658
659
660
661
662
663
664
665
666
667
668
669
670
671
672
673
674
675
676
677
678
679
680
681
682
683
684
685
686
687
688
689
690
691
692
693
694
695
696
697
698
699
700
701
702
703
704
705
706
707
708
709
710
711
712
713
714
715
716
717
718
719
720
721
722
723
724
725
726
727
728
729
730
731
732
733
734
735
736
737
738
739
740
741
742
743
744
745
746
747
748
749
750
751
752
753
754
755
756
757
758
759
760
761
762
763
764
765
766
767
768
769
770
771
772
773
774
775
776
777
778
779
780
781
782
783
784
785
786
787
788
789
790
791
792
793
794
795
796
797
798
799
800
801
802
803
804
805
806
807
808
809
810
811
812
813
814
815
816
817
818
819
820
821
822
823
824
825
826
827
828
829
830
831
832
833
834
835
836
837
838
839
840
841
842
843
844
845
846
847
848
849
850
851
852
853
854
855
856
857
858
859
860
861
862
863
864
865
866
867
868
869
870
871
872
873
874
875
876
877
878
879
880
881
882
883
884
885
886
887
888
889
890
891
892
893
894
895
896
897
898
899
900
901
902
903
904
905
906
907
908
909
910
911
912
913
914
915
916
917
918
919
920
921
922
923
924
925
926
927
928
929
930
931
932
933
934
935
936
937
938
939
940
941
942
943
944
945
946
947
948
949
950
951
952
953
954
955
956
957
958
959
960
961
962
963
964
965
966
967
968
969
970
971
972
973
974
975
976
977
978
979
980
981
982
983
984
985
986
987
988
989
990
991
992
993
994
995
996
997
998
999
1000
1001
1002
1003
1004
1005
1006
1007
1008
1009
1010
1011
1012
1013
1014
1015
1016
1017
1018
1019
1020
1021
1022
1023
1024
1025
1026
1027
1028
1029
1030
1031
1032
1033
1034
1035
1036
1037
1038
1039
1040
1041
1042
1043
1044
1045
1046
1047
1048
1049
1050
1051
1052
1053
1054
1055
1056
1057
1058
1059
1060
1061
1062
1063
1064
1065
1066
1067
1068
1069
1070
1071
1072
1073
1074
1075
1076
1077
1078
1079
1080
1081
1082
1083
1084
1085
1086
1087
1088
1089
1090
1091
1092
1093
1094
1095
1096
1097
1098
1099
1100
1101
1102
1103
1104
1105
1106
1107
1108
1109
1110
1111
1112
1113
1114
1115
1116
1117
1118
1119
1120
1121
1122
1123
1124
1125
1126
1127
1128
1129
1130
1131
1132
1133
1134
1135
1136
1137
1138
1139
1140
1141
1142
1143
1144
1145
1146
1147
1148
1149
1150
1151
1152
1153
1154
1155
1156
1157
1158
1159
1160
1161
1162
1163
1164
1165
1166
1167
1168
1169
1170
1171
1172
1173
1174
1175
1176
1177
1178
1179
1180
1181
1182
1183
1184
1185
1186
1187
1188
1189
1190
1191
1192
1193
1194
1195
1196
1197
1198
1199
1200
1201
1202
1203
1204
1205
1206
1207
1208
1209
1210
1211
1212
1213
1214
1215
1216
1217
1218
1219
1220
1221
1222
1223
1224
1225
1226
1227
1228
1229
1230
1231
1232
1233
1234
1235
1236
1237
1238
1239
1240
1241
1242
1243
1244
1245
1246
1247
1248
1249
1250
// Copyright 2015-2024 The Khronos Group Inc.
//
// SPDX-License-Identifier: CC-BY-4.0

[[extensions]]
= API Versions, Extensions, and Layers

This chapter describes required and recommended processes for writing
specification language for different core API versions, extensions, and API
layers.
It is concerned with processes and registration, while fine-grained naming
conventions are included in the <<naming,API Naming Conventions chapter>>.

[NOTE]
.Note
====
The mechanism and process of specifying extensions is subject to change, as
we receive feedback from authors and further requirements of documentation
tooling.
This document will be updated as changes are made.
====


== Introduction

The Khronos extension registries and extension naming conventions serve
several purposes:

  * Avoiding naming collisions between extensions developed by mutually
    unaware parties, both in the extension names themselves, as well as
    their token, command, and type names.
  * Allocating enumerant values for tokens added by extensions
  * Creating a defined order between extensions.
    Extensions with higher numbers may have dependencies upon extensions
    with lower numbers, and must define any relevant interactions with
    lower-numbered extensions.
  * Provides a central repository for documentation and header changes
    associated with extensions


== Proposing New Extensions

The first step in the process should be to fill out a proposal document, and
iterate on that before committing to writing specification language.

The main reasons to do this are to ensure that everyone understands the
nature of the problem being addressed, to be clear why a particular solution
was chosen in lieu of others, and to allow for design changes before
committing to specification text.
If a potential implementor has concerns with any of the design choices, it
is much easier to change details in a proposal document than it is to
rewrite specification text.

In the top level `proposals` folder there is a template (`template.adoc`)
for writing design proposals, including guidance on how it should be used.

For some simpler extensions it may not be necessary to write a proposal
document if both the problem is well understood and the solution well
bounded, so this is not a required piece of documentation.
However it may still be useful to write this in a proposal document.

Once a proposal is written, the Vulkan Working Group and other interested
parties should be asked to review and provide feedback before specification
work begins.


[[extensions-rules]]
== General Rules/Guidelines

Some general rules to simplify the specific rules below:

  * API versions, extensions and layers must each have a globally unique
    name.
  * All commands and tokens must have a globally unique name.
  * API versions and extensions can expose new commands, types, and/or
    tokens, but layers must not.
  ** However, layers can expose their own extensions, which in turn are
     allowed to expose new commands and tokens.
  * All extensions must be registered with Khronos.
  * Extensions in general are strictly additive and backwards-compatible
    with each other and with the core API.
    However, as described in more detail the Fundamentals chapter of the
    <<vulkan-spec,Vulkan API Specification>>, explicit incompatibilities may
    exist, and must be documented.


[[extensions-naming-conventions]]
== Version, Extension, and Layer Naming Conventions

Versions, extensions and layers have formal _names_.
These names are used in a variety of places:

  * When specifying extensions and layers to enable in the API.
  * As a preprocessor symbol in the `vulkan_*.h` header files indicating
    that an extension interface is defined at compile time.
  * To control building the Vulkan Specification from asciidoctor source
    containing multiple versions and extensions, by explicitly enabling
    their inclusion.

[NOTE]
.Note
====
Published extensions are documented as part of the default branch (`main`)
of the <<vulkan-docs,KhronosGroup/Vulkan-Docs>> project.
They can optionally be included or excluded when generating specifications.
====

There is a rigid syntax for these names:

  * Versions are named with the syntax `VK_VERSION_<major>_<minor>`.
  * Extensions are named with the syntax `VK_<author>_<name>`.
  * Layers are named with the syntax `VK_LAYER_<author>_<name>` or
    `VK_LAYER_<fqdn>_<name>`.

All these names include a `VK_` prefix, as described in the
<<naming-preprocessor,Preprocessor Defines>> section above.
In addition, layers add a `LAYER_` prefix.

All these names must be valid C language identifiers.


[[extensions-naming-conventions-name-strings]]
=== Version, Extension and Layer Name Strings

The `<name>` portion of version, extension and layer names is a concise name
describing its purpose or functionality.
The underscore (`_`) character is used as a delimiter between words.
Every alphabetic character of the name must be in lower case.


[[extensions-naming-author-IDs]]
=== Author IDs for Extensions and Layers

Extension and layer names also contain an _author ID_, indicated by
`<author>` above, identifying the author of the extension/layer.
This ID is a short, capitalized string identifying an author, such as a
Khronos member developing Vulkan implementations for their devices, or a
non-Khronos developer creating Vulkan layers.
Author IDs must be registered with Khronos.

Some authors have platform communities they wish to distinguish between, and
can register additional author IDs for that purpose.
For example, Google has separate Android and Chrome communities with
separate author IDs.
This is represented in the <<extensions-api-registry, API registry>> as:

[source, xml]
----
<tag name="ANDROID"  author="Google LLC" contact="contactperson @githubusername"/>
<tag name="CHROMIUM" author="Google LLC" contact="contactperson @githubusername"/>
----

In the above example, `Google LLC` is the author for two author IDs
(`ANDROID` and `CHROMIUM`).

Details on how to register an author ID are provided below.
Layer authors not wishing to register an author ID with Khronos can instead
use a fully-qualified domain name (FQDN, indicated by `<fqdn>` above) as the
ID.
The FQDN should be a domain name owned by the author.
FQDNs cannot be used for extensions, only for layers.

_Vendor extensions_ are used for functionality that is, at least initially,
specific to a single registered author or platform (e.g. Android).
These extensions are not ratified by Khronos.
Typically, they are only implemented by the registered author or by
implementations that support the target platform.

Khronos has registered some author IDs for specific uses:

  * KHR is used for Khronos-ratified extensions.
  * EXT is used for multi-vendor extensions.
    These are extensions intended to be exposed by implementations from
    multiple vendors.
    Historically these extensions were not ratified, but Khronos has begun
    retroactively ratifying selected `EXT` extensions.

[NOTE]
.Note
====
The `KHX` author ID was used for _experimental_ extensions, as described in
the "`Layers & Extensions`" appendix of the <<vulkan-spec,Vulkan API
Specification>>.
As of the initial Vulkan 1.1 public release, all `KHX` extensions have been
promoted to `KHR` status, and this mechanism is no longer used.
====

The following author IDs are reserved and must _not_ be used:

  * `VK` - To avoid confusion with the top-level `VK_` prefix.
  * `VULKAN` - To avoid confusion with the name of the Vulkan API.
  * `LAYER` - To avoid confusion with the higher-level "`LAYER`" prefix.
  * `KHRONOS` - To avoid confusion with the Khronos organization.

The following is a summary of extension and layer names, demonstrating the
cases described above:

  * Extension names all use the base prefix `VK_`.
  * Khronos-ratified extensions add the reserved author ID `KHR` and use the
    prefix `VK_KHR_`.
  * Multi-vendor extensions add the special author ID `EXT` to the base
    prefix, and will use the prefix `VK_EXT_`.
  * Vendor extensions add the author ID to the base prefix.
    For example, NVIDIA will use the prefix `VK_NV_`, and Valve will use the
    prefix `VK_VALVE_`.
  * Layer names follow the same conventions as extensions, but use the base
    prefix `VK_LAYER_`.
  * Because layers need not be registered with Khronos, an alternative
    mechanism is needed to allow creating unique layer names without
    registering an author ID.
    Layer authors that prefer not to register an author ID can instead use a
    fully-qualified domain name (FQDN) in reverse-order as an author ID,
    replacing `.` (period) with `_` (underscore) characters.
    The restriction that layer names must be valid C identifiers means that
    some FQDNs cannot be used as part of layer names.


[source, c]
.Example
----
// Core API version name for Vulkan 1.1
VK_VERSION_1_1

// Khronos ratified extension name
VK_KHR_mirror_clamp_to_edge

// Multi-vendor extension name
VK_EXT_debug_marker

// Vendor extension name using author ID NV
VK_NV_glsl_shader

// Vendor layer name using author ID LUNARG
VK_LAYER_LUNARG_vktrace

// Layer name using the FQDN www.3dxcl.invalid instead of an author ID
VK_LAYER_invalid_3dxcl_www
----

[NOTE]
.Note
====
To avoid linking to a nonexistent domain, the reserved TLD `.invalid` is
used in the example above.
====


[[extensions-naming]]
== Extension Command, Type, and Token Naming Conventions

Extensions may add new commands, types, and tokens, or collectively
"`objects`", to the Vulkan API.
These objects are given globally unique names by appending the author ID
defined above for the extension name as described in the
<<naming-extension-identifiers, Extension Identifier Naming Conventions>>
section above.


[[extensions-api-registry]]
== The Vulkan API Registry

The canonical definition of the Vulkan APIs is kept in an XML file known as
the *Vulkan API Registry*.
The registry is kept in `xml/vk.xml` in the default branch (`main`) of the
<<vulkan-docs,KhronosGroup/Vulkan-Docs>> project, containing the most
recently released Vulkan API specification.
The registry contains reserved author IDs, core and extension interface
definitions, definitions of individual commands and structures, and other
information which must be agreed on by all implementations.
The registry is used to maintain a single, consistent global namespace for
the registered entities, to generate the Khronos-supplied Vulkan header
files, and to create a variety of related documentation used in generating
the API specification and reference pages.
Other uses of the registry outside Khronos include the LunarG Loader and
Validation Layers, and a variety of language bindings.


[[extensions-author-ID]]
== Registering an Author ID With Khronos

Previous Khronos APIs could only officially be modified by Khronos members.
In an effort to build a more flexible platform, Vulkan allows non-Khronos
developers to extend and modify the API via layers and extensions in the
same manner as Khronos members.
However, extensions must still be registered with Khronos.
A mechanism for non-members to register layers and extensions is provided.

Extension authors will be able to create an account on GitHub and register
an author ID with Khronos through the
<<vulkan-docs,KhronosGroup/Vulkan-Docs>> project.
The author ID must be used for any extensions that author registers.
The same mechanism will be used to request registration of extensions or
layers with Khronos, as described below.

To reserve an author ID, propose a merge request against
<<extensions-api-registry,`vk.xml`>> in the default branch.
The merge must add a `<tag>` XML tag and fill in the `name`, `author` and
`contact` attributes with the requested author ID, the author's formal name
(e.g. company or project name), and contact email address, respectively.
The author ID will only be reserved once this merge request is accepted.

Please do not try to reserve author IDs which clearly belong to another
existing company or project which may wish to develop Vulkan extensions or
layers in the future, as a matter of courtesy and respect.
Khronos may decline to register author IDs that are not requested in good
faith.


[[extensions-vendor-id]]
== Registering a Vendor ID With Khronos

Vulkan implementors must report a valid vendor ID for their implementation
when queried by fname:vkGetPhysicalDeviceProperties, as described in the
"`Devices and Queues`" section of the <<vulkan-spec,Vulkan API
Specification>>.
If there is no valid PCI vendor ID defined for the physical device,
implementations must obtain a Khronos vendor ID.

Khronos vendor IDs are reserved in a similar fashion to
<<extensions-author-ID,author IDs>>.
While vendor IDs are not directly related to API extensions, the reservation
process is similar, and so is described in this section.

To reserve an Khronos vendor ID, you must first have a Khronos author ID.
Propose a merge request against <<extensions-api-registry,`vk.xml`>> in the
default branch.
The merge must define a new enumerant by adding an `<enum>` tag to the
`VkVendorId` `<enums>` tag, following the existing examples.
The `value` attribute of the `<enum>` must be the next available unused
value, and is the reserved vendor ID.
The `name` attribute must be `VK_VENDOR_ID_<author>`, where `<author>` is
the author tag.
The vendor ID will be reserved only once this merge request has been
accepted.

Please do not try to reserve vendor IDs unless you are making a good faith
effort to develop an implementation of a Khronos API and require one for
that purpose.

[NOTE]
.Note
====
Other Khronos APIs such as OpenCL also utilize vendor IDs and share the
Khronos vendor ID space.
To obtain a vendor ID for these APIs, first reserve it in Vulkan's `vk.xml`
and once that is done, utilize it in the other API.
To avoid collisions, we are currently utilizing `vk.xml` as the central
Khronos vendor ID registry.
====


== Registering Extensions and Layers

Extensions must be registered with Khronos.
Layers should be registered, but registration is not required.
Registration means:

  * Receiving an extension number.
  * Adding the extension or layer name to the list in `vk.xml` and appearing
    on the Khronos registry website, which will link to associated
    documentation hosted on Khronos.
  * For extensions which add to the Vulkan API, including definitions of
    those additions to `vk.xml`.

Registration for Khronos members is handled by filing a merge request in the
internal gitlab repository modifying `vk.xml` in the default branch,
containing the core specification against which the extension or layer will
be written.
Registration is not complete until the registry maintainer has validated and
accepted the merge.

A similar mechanism is used to register extensions not authored by Khronos
members.
Implementors who are not Khronos members and who need to create extensions
must register with Khronos by creating a GitHub account, and registering
their author ID and/or FQDNs to that account.
They can then submit new extension registration requests by proposing merges
to `vk.xml`.
On acceptance of the merge, the extension will be registered, though its
specification need not be checked into the Khronos GitHub repository at that
point.

The registration process can be split into several steps to accommodate
extension number assignment prior to extension publication:

  * Acquire an extension number.
    This is done by proposing a merge request against `vk.xml` similarly to
    how <<extensions-author-ID,author IDs are reserved>>.
    The merge should add a new `<extension>` tag at the end of the file with
    attributes specifying the proposed extension `name`, the next unused
    sequential extension `number`, the `author` and `contact` information
    (if different than that already specified for the author ID used in the
    extension name), and finally, specifying `supported="disabled"`.
    The extension number will be reserved only once this merge request is
    accepted into the default branch.
  * Develop and test the extension using the registered extension number.
  * Publish the extension to Khronos using the previously registered
    extension number, by submitting merge requests to the default branch
    defining the changes specific to the extension.
    Changes to both the specification source, and to `vk.xml` will be
    needed.
  ** Extension changes to the specification source must be protected by
     asciidoctor conditionals as described in the
     <<extensions-documenting,Documenting Extensions>> section.
  ** Changes to `vk.xml` must define the extension interfaces in the
     `<extension>` block, and must also change the `supported` attribute
     value of the `<extension>` to `supported="vulkan"`.
  ** When publishing an extension, mark it as enabled by proposing a merge
     to the default branch changing the `supported` attribute value of the
     `<extension>` to `supported="vulkan"`.
  ** Once the merge request defining an extension has been accepted into the
     default branch, publication is complete - although it may not be
     visible on GitHub until the next regular core Specification update is
     pushed out.
  ** Publishing on the <<vulkan-docs,Khronos public GitHub repository>> is
     preferred when possible.
     Khronos members may instead create branches on Khronos' internal gitlab
     server, but those branches will eventually be mirrored to GitHub.
  * It is still possible to publish a separate branch of the repository with
    appropriate changes relative to the core Vulkan API branch instead, but
    this approach is deprecated and discouraged.
    If this is done, all changes to `vk.xml` must still be made in the
    default branch.


[[extensions-documenting]]
== Documenting API Versions and Extensions

API versions and extensions are documented as modifications to the Vulkan
specification.
Changes specific to a version or extension are protected by asciidoctor
conditionals.
The changes are only visible in generated documentation when the
Specification is built with an asciidoctor attribute of that name defined.
Khronos publishes three forms of the Vulkan Specification: the core API
(e.g. versions 1.x) only; core API with all registered `KHR` and `EXT`
extensions; and core API with all registered extensions.


[[extensions-documenting-extensions]]
=== Changes for New Extensions

If an new extension, or a related group of them is of sufficient scope to
require a new chapter of the specification, localize such changes into a
small number of asciidoctor include files located under a subdirectory with
the name of the extension.
An example can be found in `chapters/VK_KHR_surface/wsi.adoc`.
Most extensions are not entirely self-contained, and also require changes in
existing parts of the specification to document new interactions.
Such changes should be inline in existing chapters.

Extensions may also require small additions to `vk.xml`, in addition to
defining the extension interfaces themselves, for purposes such as
introducing new return codes or extending structures to existing APIs.

[NOTE]
.Note
====
We do not yet fully document an example of including a new version or
extension.
New versions are authored only by Khronos and examples will be available at
such time that we publish a new version.
Extension authors should refer to the default branch and search for the
names of existing extensions, such as `VK_KHR_surface`, for markup examples.
Some aspects of the changes for this example extension are described below.
====

Changes for extensions include (but may not be limited to) the following:

  * All extensions must add an appendix to the Vulkan specification.
    The appendix can be modeled after the `VK_KHR_shader_float_controls`
    extension in `appendices/VK_KHR_shader_float_controls.adoc`.
    It contains metainformation about the extension as well as code
    examples, and revision history.
    Other useful references are the `VK_KHR_shader_draw_parameters`
    appendix, which includes a variety of external dependencies and
    interactions, and the `VK_EXT_debug_marker` appendix, which is a
    simpler, standalone example.
  ** The extension appendices are also incorporated in separate
     per-extension reference pages, and must rigidly follow the structure of
     the model appendices (although individual subsections can be added or
     removed as required).
  ** When creating references to the extension appendix from elsewhere in
     the Specification, use the custom macro `apiext:`, instead of an
     explicit asciidoctor link.
     This allows more easily checking for invalid extensions, and changing
     the link target for generated reference pages and other alternate
     output forms.
+
--
[source,asciidoc]
.Example Markup
----
A link to the `apiext:VK_KHR_shader_float_controls` extension.

Do not use this (old) form: `<<VK_KHR_shader_float_controls>>`.
----

[NOTE]
.Note
====
If you are converting an old branch with extension references in it to use
the `apiext:` macro, you can use this shell script:

[source,sh,subs=attributes+]
----
sed -i -E 's/`?<<(VK_[A-Za-z0-9_]*)>>`?/`apiext:\1`/g' chapters/{*.adoc,*/*.adoc} appendices/*.adoc
----
====
--
  * In the preamble to the appendix, start with an asciidoctor `include` of
    the automatically generated meta information.
    This information includes the extension name string, type, number,
    revision, and contact information from `vk.xml`.
  * Following the `include`, add an *Other Extension Metadata* subsection
    containing as many of the following items as are meaningful:
  ** *Status* - *Complete*, *Draft*, or other.
     When an extension is published in the default branch, it is normally
     assumed to be complete; the *Status* field should be removed at this
     time, unless it contains additional information.
  ** *Last Modified Date* - if wanted, although git log queries can provide
     equivalent information.
  ** *IP Status* - Such as *No known IP claims*, or more specific
     information if there are known IP claims and the extension has, or has
     not been ratified by the Khronos Board of Promoters.
  ** *Interactions and External Dependencies* - may include requirements or
     interactions with optional Vulkan features, SPIR-V (`SPV`) and OpenGL
     extensions, and interactions (other than strictly requiring) with other
     Vulkan extensions.
  ** *Contributors* - Names and corporate affiliations of people who have
     made significant direct contributions to this extension.
  * Following these items, add whitespace followed by a *Description*
    section.
    The first paragraph of this section should be a compact, standalone
    description of the extension's functionality and purpose, suitable for
    use in summaries of new functionality such as press releases or the
    Vulkan change log.
    Additional paragraphs expanding on the description may be added at the
    author's discretion.
  * If the extension has been deprecated or promoted, add *Deprecation*
    and/or *Promotion* sections describing these actions.
    There is standard boilerplate *Promotion* language used when promoting
    to a Vulkan core version.
    For example, see `appendices/VK_EXT_descriptor_indexing.adoc for
    language used when promoting to Vulkan core, with some features made
    optional in the promoted version.
  * Next, add an asciidoctor `include` of the automatically generated
    interface information.
    This information includes API entities defined by the extension in
    `vk.xml`, such as new commands, structures, enumerants, and so on.
  * Following the `include`, add subsections describing interface
    information for SPIR-V shading capabilities not captured in `vk.xml`,
    such as:
  ** *New SPIR-V Capabilities* (include xrefs to the appropriate new section
     of the List of SPIR-V Capabilities in `appendices/spirvenv.adoc`).
  ** *New or Modified Built-In Variables* (include xrefs to the appropriate
     new section of the Interfaces chapter).
  ** *New Variable Decorations* (include xrefs to the appropriate new
     section of the Interfaces chapter).
  * Finally, add subsections describing other information about the
    extension, such as:
  ** *Issues* (in itemized list style, describing each significant issue
     raised during development of the extension, and its resolution).
  ** *Version History* (in itemized list style, describing significant
     functional changes to the extension during its development).
  * Each extension's appendix file is automatically included from
    `appendices/extensions.adoc` via code generated from `vk.xml`.
    It is not necessary to explicitly include the appendices.
  * Extensions usually make significant additions and changes to the Vulkan
    specification.
    They often add an entirely new chapter, or a new section of an existing
    chapter, defining the new commands, structures, and enumerants.
    For example, in the case of `VK_EXT_debug_marker`, it adds a new section
    of the "`Debugging`" chapter in `chapters/debugging.adoc`, by including
    in that file:
+
[source,asciidoc]
.Example Markup
----
\ifdef::VK_EXT_debug_marker[]
\include::{chapters}/VK_EXT_debug_marker/wsi.adoc[]
\endif::VK_EXT_debug_marker[]
----
  * In every other place where the extension alters the behavior of the core
    Specification, make such changes and protect the modifications with the
    same asciidoctor conditionals.
    For example, `VK_KHR_surface` adds new error codes to Vulkan.
    These are added to `chapters/fundamentals.adoc` in the "`Return Codes`"
    section as follows:
+
[source,asciidoc]
.Example Markup
----
... list of existing error codes
\ifdef::VK_KHR_surface[]
\include::{chapters}/VK_KHR_surface/VkResultErrorDescriptions_surface.adoc[]
\endif::VK_KHR_surface[]
----
  * If two extensions interact, the asciidoctor conditionals must be
    carefully structured so as to properly document the interactions if the
    specification is built with both extensions.
    Asciidoc conditionals allow
    link:{docguide}/directives/ifdef-ifndef/#checking-multiple-attributes[AND
    and OR constructs].
+
[source,asciidoc]
.Example Markup
----
\ifdef::VK_KHR_foo[]
... discussion of VK_KHR_foo ...
\ifdef::VK_KHR_fum[]
... discussion of interactions between VK_KHR_foo and VK_KHR_fum ...
\endif::VK_KHR_fum[]
\endif::VK_KHR_foo[]

\ifdef::VK_KHR_fum[]
... discussion of VK_KHR_fum ...
\endif::VK_KHR_fum[]
----
  * In cases where a new extension (A) modifies both core and an existing
    extension (B), if the new extension (A) becomes part of the core at a
    future release (i.e. is no longer an extension), the portion of the new
    extension that modified the existing extension (B) effectively becomes
    part of that existing extension.
    Thus, at the new core release, enabling the pre-existing extension (B)
    also enables the functionality that was previously enabled by enabling
    the previously-new extension (A).
  * For vendor extensions, changes made to existing core Specification
    source files and to `vk.xml` all fall under the Contributor License
    Agreement.
    Vendors may use their own copyright on new files they add to the
    repository, although that copyright must be compatible with the
    Specification copyright.
  * In most cases, there will be at most two new files added to the
    specification: `extensions/*extension_name*.adoc`, and
    `chapters/*extension_name*.adoc`.
    If you need more than one new file in either the `chapters/` or
    `extensions/` directories, create a subdirectory named with the
    extension name and place the new files there.
    For example, instead of `chapters/VK_KHR_android_surface.adoc`, there is
    `chapters/VK_KHR_android_surface/platformCreateSurface_android.adoc` and
    `chapters/VK_KHR_android_surface/platformQuerySupport_android.adoc`,
    both of which are conditionally included elsewhere in the core
    specification files.
  * Valid usage statements referring to interactions between structures in a
    pname:pNext chain must be described in the parent structure's language,
    as specified <<extensions-interactions-parent, in more detail below>>.
  * Valid usage statements should be written including all relevant version
    and extension information embedded in the text, and surrounded by
    preprocessor directives as necessary, rather than simply relying on an
    `ifdef` to take care of it.
    For example, instead of:
+
[source,asciidoc]
.Example Markup
----
\ifndef::VK_VERSION_1_3[]
  * At least one of the following must: be true:
\ifdef::VK_EXT_extended_dynamic_state[]
  ** the <<features-extendedDynamicState, pname:extendedDynamicState>>
     feature is enabled
\endif::VK_EXT_extended_dynamic_state[]
\ifdef::VK_EXT_shader_object[]
  ** the <<features-shaderObject, pname:shaderObject>>
     feature is enabled
\endif::VK_EXT_shader_object[]
\endif::VK_VERSION_1_3[]
----
+
where the version overrides the need for the features, add a condition for
the version too:
+
[source,asciidoc]
.Example Markup
----
  * At least one of the following must: be true:
\ifdef::VK_EXT_extended_dynamic_state[]
  ** the <<features-extendedDynamicState, pname:extendedDynamicState>>
     feature is enabled
\endif::VK_EXT_extended_dynamic_state[]
\ifdef::VK_EXT_shader_object[]
  ** the <<features-shaderObject, pname:shaderObject>>
     feature is enabled
\endif::VK_EXT_shader_object[]
\ifdef::VK_VERSION_1_3[]
  ** the value of slink:VkApplicationInfo::pname:apiVersion used to create
     the slink:VkInstance parent of pname:commandBuffer is greater than or
     equal to Version 1.3
\endif::VK_VERSION_1_3[]
----

When writing language dependent on the interaction of multiple extensions,
asciidoctor conditional syntax is very restricted and only supports a single
level of logical AND (`+`) or OR (`,`) operators.
For example, if a section of text only applies when one extensions is
enabled and another is not, the following markup will not work:

[source,asciidoc]
.Example Markup (Does Not Work)
----
\ifdef::VK_KHR_shader_float16_int8+!VK_KHR_8bit_storage[]
This should only appear if VK_KHR_shader_float16_int8 is defined and
VK_KHR_8bit_storage is not defined.
\endif::VK_KHR_shader_float16_int8+!VK_KHR_8bit_storage[]
----

Instead, expand the complex conditional into nested simpler ones:

[source,asciidoc]
.Example Markup (Does Work)
----
\ifdef::VK_KHR_shader_float16_int8[]
\ifndef::VK_KHR_8bit_storage[]
This should only appear if VK_KHR_shader_float16_int8 is defined and
VK_KHR_8bit_storage is not defined.
\endif::VK_KHR_8bit_storage[]
\endif::VK_KHR_shader_float16_int8
----


[[extensions-documenting-versions]]
=== Changes for New API Versions

When creating a new version of the core API, such as Vulkan 1.1, changes are
done similarly to extensions, with the following differences:

[NOTE]
.Note
====
This list is being developed in conjunction with the Vulkan 1.1
Specification, is probably incomplete, and is subject to change.
Items marked *TBD* are still being discussed within the Vulkan Working
Group.
====

  * New API versions will be more tightly integrated into the specification
    sources than extensions, although it is still helpful to partition
    changes into new files when they are sufficiently self-contained.
  * New API versions must add an appendix to the Vulkan specification.
    Unlike the extension appendices, this appendix simply summarizes release
    information (dates of Ratification by the Khronos Board of Promoters,
    and of public release), the contributor list, and high-level
    descriptions of new features in this version (including the names of any
    extensions promoted to core status in this version).
  ** TBD - we might choose to include a new API summary with links into the
     specification body for new features, as well.
  * TBD - how to name and where to include this appendix file.
  * Changes to the Specification for new versions will range from small
    changes to existing language, to new commands and structures, to adding
    entire new chapters.
    New chapters must be defined in separate files under the `chapters/`
    directory, and included at an appropriate point in `vkspec.adoc` or
    other specification source files.
    Other changes and additions are included inline in existing chapters.
  * All changes that are specific to the new version must be protected by
    the asciidoctor conditional (e.g. the version name).
    For example, in the case of Vulkan 1.1:
+
[source,asciidoc]
.Example Markup
----
Add a new chapter:

\ifdef::VK_VERSION_1_1[]
\include::{chapters}/newchapter11.adoc[]
\endif::VK_VERSION_1_1[]

Add a new feature:

\ifdef::VK_VERSION_1_1[]
... language describing the new command, structure, or enumeration
\endif::VK_VERSION_1_1[]
----
  * The specification must continue to be a valid document when the new
    version is *not* defined, so that (for example) the Vulkan 1.1 branch
    specification can continue to be updated.
  * TBD - how to deprecate extensions which have been promoted to core
    status in the new version, while continuing to have those extensions
    appear then older versions of the specification are being built.
  * The same constraints <<extensions-documenting-extensions, described
    above>> for Valid Usage statements modified by extensions apply for new
    versions.


[[extensions-assigning-token-values]]
== Assigning Extension Token Values

Extensions can define their own enumeration types and assign any values to
their enumerants that they like.
Each enumeration has a private namespace, so collisions are not a problem.
However, when extending existing enumeration objects with new values, care
must be taken to preserve global uniqueness of values.
Enumerations which define new bits in a bitmask are treated specially as
described in <<extensions-reserving-bitmask-values,Reserving Bitmask
Values>> below.

Each extension is assigned a range of values that can be used to create
globally-unique enum values.
Most values will be negative numbers, but positive numbers are also
reserved.
The ability to create both positive and negative extension values is
necessary to enable extending enumerations such as etext:VkResult that
assign special meaning to negative and positive values.
Therefore, 1000 positive and 1000 negative values are reserved for each
extension.
Extensions must not define enum values outside their reserved range without
explicit permission from the owner of those values (e.g. from the author of
another extension whose range is infringed on, or from the Khronos Registrar
if the values do not belong to any extension's range).

[NOTE]
.Note
====
Typically, extensions use a unique offset for each enumeration constant they
add, yielding 1000 distinct token values per extension.
Since each enumeration object has its own namespace, if an extension needs
to add many enumeration constant values, it can reuse offsets on a per-type
basis.
====

The information needed to add new values to the XML are as follows:

  * The **extension name** (e.g. `VK_KHR_swapchain`) that is adding the new
    enumeration constant.
  * The existing enumeration **type** being extended (e.g.
    stext:VkStructureType).
  * The name of the new enumeration **token** being added (e.g.
    etext:VK_STRUCTURE_TYPE_SWAPCHAIN_CREATE_INFO_KHR).
  * The **offset**, which is an integer between 0 and 999 relative to the
    base being used for the extension.
  * The **direction** may be specified to indicate a negative value
    (`dir="-"`) when needed for negative etext:VkResult values indicating
    errors, like etext:VK_ERROR_SURFACE_LOST_KHR.
    The default direction is positive, if not specified.
  * The **extension number** is usually implicit and taken from metadata of
    the extension being defined.
    It is used to create a range of unused values specific to that
    extension.

Individual enumerant values are calculated as offsets in the range defined
by the extension number, as follows:

  * [eq]#_base_value_ = 1000000000#
  * [eq]#_range_size_ = 1000#
  * [eq]#enum_offset(_extension_number_, _offset_) = _base_value_ {plus}
    (_extension_number_ - 1) {times} _range_size_ + _offset_#
  * Positive values: [eq]#enum_offset(_extension_number_, _offset_})#
  * Negative values: [eq]#enum_offset(_extension_number_, _offset_})#

The exact syntax for specifying extension enumerant values is defined in the
<<vulkan-registry, Vulkan API Registry>> schema documentation.
Extension authors should also refer to existing extensions for examples.

If an extension is promoted to another extension or to a core API version,
the enumerant values should remain the same as they were in the original
extension, in order to maintain binary compatibility with existing
applications.
In this case, the extension number will need to be specified explicitly to
keep the promoted enumerant value unchanged.


[[extensions-reserving-bitmask-values]]
=== Reserving Bitmask Values

Enumerants which define bitmask values are a special case, since there are
only a small number of unused bits available for extensions.
For core Vulkan API and KHR extension bitmask types, reservations must be
approved by a vote of the Vulkan Working Group.
For EXT and vendor extension bitmask types, reservations must be approved by
the listed contact of the extension.
Bits are reserved in the same fashion as extension numbers, by creating a
placeholder reservation for each bit in the disabled XML `<extension>` block
for that extension in the default branch.
Once the extension is ready to be merged into the default branch, the
`<extension>` block is updated with the actual name.
An example reservation for a disabled extension is:

[source,xml]
----
<extension name="VK_AMD_extension_24" number="24" author="AMD" supported="disabled">
  <require>
    <enum bitpos="6" extends="VkQueueFlagBits" name="VK_QUEUE_RESERVED_6_BIT_KHR"/>
----

Bit position 31 may not be used, due to inconsistent behavior by C
compilers.
This is enforced by the generator scripts.

[NOTE]
.Note
====
Because of the way in which extension bitmask values are assigned inside the
XML `<extension>` tag, it is not always obvious what the next free bit in a
bitmask type is, or when a collision occurs.
The most straightforward way to determine the next free bit for a given
bitmask type is to look at the declaration of that type in the generated
header files.
When generating the headers, the script will raise warnings about "`Two
enums found with the same value`" that will help identify this problem.
====

When a 32-bit flags type is close to running out of bits, a corresponding
64-bit flag type may be created for use with new interfaces, such as the
tlink:VkAccessFlags and tlink:VkAccessFlags2KHR types.
These flag types have corresponding 32- and 64-bit bitmask types
(elink:VkAccessFlagBits and elink:VkAccessFlagBits2KHR).
When reserving remaining bits at bit positions 0 through 30, a similarly
named bit should be reserved in both bitmask types
(ename:VK_ACCESS_MEMORY_READ_BIT and ename:VK_ACCESS_2_MEMORY_READ_BIT), to
avoid having the same bit used for different purposes in two otherwise very
similar interfaces.
If that usage is not actually supported by one or the other bitmask type,
the bit should still be reserved, but commented out in the XML.

[NOTE]
.Note
====
The existing reservation mechanism used for in-development extensions does
not work well for non-disabled extensions.
So we currently do not have a good way of semantically indicating that a bit
is reserved, but should not appear in the header file, for a non-disabled
extension, and an XML comment reserving the bit is a workaround.
This case will come up very rarely.
====


[[extensions-new-flags-types]]
== New Flags and Bitmask Types

When an extension introduces a new flags (etext:*Flags) type, it should also
introduce a corresponding new bitmask (etext:*FlagBits) type.
The flags type contains zero more more bits from the bitmask, and is used to
specify sets of bits for commands or structures.

In some cases, a new flags type will be defined with no individual bits yet
specified.
This usage occurs when the flags are intended for future expansion.
In this case, even though the corresponding bitmask type is not yet useful,
the (empty) bitmask type should be defined in `vk.xml`.
The empty bitmask type and corresponding flags type should be given
boilerplate definitions in the specification.


== Required Extension Tokens

In addition to any tokens specific to the functionality of an extension, all
extensions must define two additional tokens.

  * `VK_EXTNAME_SPEC_VERSION` is an integer constant which is the revision
    of the extension named `VK_extname` (`EXTNAME` is all upper-case, while
    extname is the capitalization of the actual extension name).
    This value begins at 1 when an extension specification is first
    published (pre-release versions may use an internal numbering scheme
    that is reset at release time), and is incremented when changes are
    made.
    Note that the revision of an extension defined in the Vulkan header
    files and the revision supported by the Vulkan implementation (the
    pname:specVersion field of the sname:VkExtensionProperties structure
    corresponding to the extension and returned by one of the
    link:html/vkspec.html#extendingvulkan-extensions[extension queries]) may
    differ.
    The revision value indicates a patch version of the extension
    specification, and differences in this version number maintain full
    compatibility, as defined in the "`Compatibility Guarantees`" section of
    the <<vulkan-spec,Vulkan API Specification>>.

[NOTE]
.Note
====
Any changes requiring the addition or removal of a type or command should be
done by creating a new extension.
The resulting extension should take care to include the appropriate
dependency information on the original extension.
====

[NOTE]
.Note
====
When the Debug Report extension (VK_EXT_debug_report) was recently updated
to include the enum values of VK_DEBUG_REPORT_OBJECT_TYPE_DISPLAY_KHR_EXT
and VK_DEBUG_REPORT_OBJECT_TYPE_DISPLAY_MODE_KHR_EXT, we violated this
policy.
That change was done prior to this revision policy clarification.
We intend to follow this policy in the future, although in exceptional
circumstances an exception may be made.
====

  * `VK_EXTNAME_EXTENSION_NAME` is a string constant which is the name of
    the extension.

For example, for the WSI extension `VK_KHR_surface`, at the time of writing
the following definitions were in effect:

[source,c]
----
#define VK_KHR_SURFACE_SPEC_VERSION 24
#define VK_KHR_SURFACE_EXTENSION_NAME "VK_KHR_surface"
----


== Extension Handles, Objects, Enums, and Typedefs

Expanding on previous discussion, extensions can add values to existing
enums; and can add their own commands, enums, typedefs, etc.
This is done by adding to <<extensions-api-registry,`vk.xml`>>.
All such additions will be included in the Vulkan header files supplied by
Khronos.

If the extension adds a new handle to Vulkan, a corresponding value must be
added to ename:VkObjectType (as defined in the "`Debugging`" section of the
<<vulkan-spec,Vulkan API Specification>>) in order to allow components to
identify and track objects of the new type.

The new enumeration value must conform to the naming defined in the
<<naming-extension-enumerant-names,Extension Enumerant Names>> section.
In this case, the type's etext:Vk prefix is replaced with the enum prefix
etext:VK_OBJECT_TYPE_, and the rest of the handle name is converted as
described in that section.

.Conversion of Handle to sname:VkObjectType Examples:
[width="70%",options="header",cols="50%,50%"]
|====
| Handle                        | sname:VkObjectType token
| VkSurfaceKHR                  | VK_OBJECT_TYPE_SURFACE_KHR
| VkDescriptorUpdateTemplateKHR | VK_OBJECT_TYPE_DESCRIPTOR_UPDATE_TEMPLATE_KHR
|====


[[extension-function_prototypes]]
== Extension Function Prototypes

Function pointer declarations and function prototypes for all core Vulkan
API commands are included in the Vulkan header files.
These come from the official XML specification of the Vulkan API hosted by
Khronos.

Function pointer declarations are also included in the Vulkan header for all
commands defined by registered extensions.
Function prototypes for extensions may be included in the headers.
Extension commands that are part of the Vulkan ABI must be flagged in the
XML.
Function prototypes will be included in the headers for all extension
commands that are part of the Vulkan ABI.

An extension can be considered platform specific, in which case its
interfaces in the header files are protected by #ifdefs.
This is orthogonal to whether an extension command is considered to be part
of the Vulkan ABI.

The initial set of WSI extension commands (i.e. for `VK_KHR_surface`,
`VK_KHR_swapchain`, and `VK_KHR_*_surface`) are considered to be part of the
Vulkan ABI.
Function prototypes for these WSI commands are included in platform-specific
files such as `vulkan_android.h`.
See the "`Window System-Specific Header Control (Informative)`" section of
the Vulkan Specification for more details.

[NOTE]
.Note
====
Based on feedback from implementors, Khronos expects the Android, Linux, and
Windows Vulkan SDKs to include our header files, and export the supported
WSI functions for those platforms from their loader libraries.
Other implementations can make different choices for their headers and
loader libraries, but are encouraged to be consistent with these
implementations.
====


== Accessing Extension Functions From Programs

fname:vkGetInstanceProcAddr and fname:vkGetDeviceProcAddr can be used in
order to obtain function pointer addresses for core and extension commands
(per the description in the "`Command Function Pointers`" section of the
<<vulkan-spec,Vulkan API Specification>>).
Different Vulkan API loaders can choose to statically export functions for
some or all of the core Vulkan API commands, and can statically export
functions for some or all extension commands.
If a loader statically exports a function, an application can link against
that function without needing to call one of the ftext:vkGet*ProcAddr
commands.

[NOTE]
.Note
====
The Vulkan API loader for Android, Linux, and Windows exports functions for
all core Vulkan API commands, and for a set of WSI extension commands that
are applicable to those operating systems (see Vulkan loader documentation
for the relevant platform/OS for details).
The WSI functions are considered special, because they are required for many
applications.
====


[[extensions-interactions]]
== Extending Structures

Extending structures modify the behavior of existing commands or structures
by providing additional parameters, using the pname:pNext field of an
existing structure to point to a chain of additional structures.
This mechanism is described in more detail in the "`Valid Usage for
Structure Pointer Chains`" section of the <<vulkan-spec,Vulkan API
Specification>>.

Multiple extending structures affecting the same structure, defined by
multiple core versions or extensions, can be chained together in this
fashion.
Any structure which can be chained in this fashion must begin with the
following two members:

["source","c++",title=""]
----
VkStructureType        sType;
const void*            pNext;
----

It is in principle possible for extensions to provide additional parameters
through alternate means, such as passing a handle parameter to a structure
with a pname:sType value defined by the extension.
This approach is strongly discouraged.

When chaining multiple extending structures together, the implementation
will process the chain starting with the base structure and proceeding
through each successive extending structure in turn.
Extending structures should behave in the same fashion no matter the order
of chaining, and must define their interactions with other extensions such
that the results are deterministic.

If an extending structure must be present in a pname:pNext chain in specific
ordering relative to other structures in the chain in order to provide
deterministic results, it must define that ordering and expected behavior as
part of its specification and valid usage statements.

[NOTE]
.Note
====
Specific ordering requirements in a pname:pNext chain are strongly
discouraged.
====

Validation of structure types in pname:pNext chains is automatically
generated from the registry, based on the description of `structextends` in
link:registry.html[the registry document].


[[extensions-interactions-parent]]
== Valid Usage and pname:pNext Chains

When there is a Valid Usage interaction between a parent structure and an
extending structure appearing in the pname:pNext chain of the parent, that
interaction must: be described in the explicit Valid Usage section of the
parent structure, rather than the extending structure, and must: be
protected by appropriate extension-specific `ifdef` constructs.

For example, a constraint added to the sname:VkImageCreateInfo structure by
the presence of structures defined by two extensions which cannot interact
is described as:

[source,asciidoc]
.Example Markup
----
// CORRECT: define interaction with children in parent VkImageCreateInfo
// structure
\ifdef::VK_NV_external_memory+VK_KHR_external_memory[]
  * If the pname:pNext chain includes a
    slink:VkExternalMemoryImageCreateInfoNV structure, it must: not include
    a slink:VkExternalMemoryImageCreateInfoKHR structure.
\endif::VK_NV_external_memory+VK_KHR_external_memory[]
----

However, a constraint added to sname:VkBufferCreateInfo by an extending
structure in the `VK_NV_dedicated_allocation` extension must not be
described as part of the extending structure's valid usage:

[source,asciidoc]
.Example Markup
----
// WRONG! Do not define interaction with parent in child
// VkDedicatedAllocationBufferCreateInfoNV structure
  * If pname:dedicatedAllocation is ename:VK_TRUE,
    sname:VkBufferCreateInfo::pname:flags must: not include
    ename:VK_BUFFER_CREATE_SPARSE_BINDING_BIT,
    ename:VK_BUFFER_CREATE_SPARSE_RESIDENCY_BIT, or
    ename:VK_BUFFER_CREATE_SPARSE_ALIASED_BIT
----

Instead, define the constraint as part of the parent
sname:VkBufferCreateInfo structure's valid usage:

[source,asciidoc]
.Example Markup
----
// REWRITTEN CORRECTLY: Define interaction with child in
// parent VkBufferCreateInfo structure
\ifdef::VK_NV_dedicated_allocation[]
  * If the pname:pNext chain includes a
    slink:VkDedicatedAllocationBufferCreateInfoNV structure, and the
    pname:dedicatedAllocation member of the chained structure is
    ename:VK_TRUE, then pname:flags must: not include
    ename:VK_BUFFER_CREATE_SPARSE_BINDING_BIT,
    ename:VK_BUFFER_CREATE_SPARSE_RESIDENCY_BIT, or
    ename:VK_BUFFER_CREATE_SPARSE_ALIASED_BIT
\endif::VK_NV_dedicated_allocation[]
----


[[extensions-feature-structures]]
== Feature Structures

A feature structure is a structure that extends
sname:VkPhysicalDeviceFeatures2 and sname:VkDeviceCreateInfo, and which
provides basetype:VkBool32 members to indicate implementation support for
individual features.

["source","c++",title=""]
----
typedef struct VkPhysicalDeviceImageRobustnessFeaturesEXT {
    VkStructureType    sType;
    void*              pNext;
    VkBool32           robustImageAccess;
} VkPhysicalDeviceImageRobustnessFeaturesEXT;
----

Every device or physical-device extension that adds or modifies device-level
commands, or adds new structures or enum values used in device-level
commands, must define a feature structure.

If an extension requires a feature structure, then any mandatory features
must be described in the Feature Requirements section.
New extensions must mandate that implementations support at least one
feature of an extension.

[source,asciidoc]
.Example Markup
----
\ifdef::VK_EXT_image_robustness[]
  * <<features-robustImageAccess, pname:robustImageAccess>>, if the
    `apiext:VK_EXT_image_robustness` extension is supported.
\endif::VK_EXT_image_robustness[]
----

For WSI extensions, it is often necessary to extend
sname:VkSurfaceCapabilities2KHR in order to enable compatibility between a
sname:VkSurface and a sname:VkPhysicalDevice to be queried.
Every device or physical-device extension that relies upon support from the
window system should implement this query.

The presence of a structure extending sname:VkSurfaceCapabilities2KHR does
not remove the requirement for a feature structure if any device-level
functionality is introduced by an extension.