working with metal—fundamentals · working with metal—fundamentals session 604 richard schreyer...

241
© 2014 Apple Inc. All rights reserved. Redistribution or public display not permitted without written permission from Apple. #WWDC14 Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games Aaftab Munshi GPU Software Engineer

Upload: others

Post on 22-May-2020

12 views

Category:

Documents


0 download

TRANSCRIPT

Page 1: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

© 2014 Apple Inc. All rights reserved. Redistribution or public display not permitted without written permission from Apple.

#WWDC14

Working with Metal—Fundamentals

Session 604 Richard Schreyer GPU Software Engineer

Graphics and Games

!

Aaftab Munshi GPU Software Engineer

Page 2: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Metal Fundamentals

Building a Metal application • Initialization

• Drawing

• Uniforms and synchronization

Metal shading language • Writing shaders in Metal

• Data types in Metal

• Shader inputs, outputs, and matching rules

Page 3: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Building a Metal Application

Richard Schreyer GPU Software

Page 4: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer
Page 5: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Building a Metal ApplicationInitialization

1. Get the Device

2. Create a CommandQueue

3. Create Resources (Buffers and Textures)

4. Create RenderPipelines

5. Create a View

Page 6: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Metal Device API

@protocol MTLDevice !

- (id <MTLCommandQueue>)newCommandQueue… - (id <MTLBuffer>)newBuffer… - (id <MTLTexture>)newTexture… - (id <MTLSampler>)newSamplerState… - (id <MTLRenderPipelineState>)newRenderPipelineState… // and much more !

@end

Page 7: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Initialization

// Get the device id <MTLDevice> device = MTLCreateSystemDefaultDevice();

Page 8: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Initialization

// Get the device id <MTLDevice> device = MTLCreateSystemDefaultDevice();

// Create a CommandQueue id <MTLCommandQueue> commandQueue = [device newCommandQueue];

Page 9: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Initialization

// Get the device id <MTLDevice> device = MTLCreateSystemDefaultDevice();

// Create a CommandQueue id <MTLCommandQueue> commandQueue = [device newCommandQueue];

// Create my Vertex Array struct Vertex vertexArrayData[3] = { … }; id <MTLBuffer> vertexArray = [device newBufferWithBytes: vertexArrayData length: sizeof(vertexArrayData) options: 0];

Page 10: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

MTLRenderPipelineDescriptor

Vertex Layout Descriptor

Vertex Shader

Fragment Shader

Blending

Framebuffer Formats

Rasterizer Coverage

Render Pipeline Descriptors

Page 11: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

MTLRenderPipelineDescriptor

Vertex Layout Descriptor

Vertex Shader

Fragment Shader

Blending

Framebuffer Formats

Rasterizer Coverage

Render Pipeline Descriptors

MTLRenderPipelineStatecompiles to

Page 12: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Create a RenderPipeline

MTLRenderPipelineDescriptor* desc = [MTLRenderPipelineDescriptor new]; !

// Set shaders id <MTLLibrary> library = [device newDefaultLibrary]; desc.vertexFunction = [library newFunctionWithName: @"myVertexShader"]; desc.fragmentFunction = [library newFunctionWithName: @“myFragmentShader"];

Page 13: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Create a RenderPipeline

MTLRenderPipelineDescriptor* desc = [MTLRenderPipelineDescriptor new]; !

// Set shaders id <MTLLibrary> library = [device newDefaultLibrary]; desc.vertexFunction = [library newFunctionWithName: @"myVertexShader"]; desc.fragmentFunction = [library newFunctionWithName: @“myFragmentShader"];

// Set framebuffer pixel format desc.colorAttachments[0].pixelFormat = MTLPixelFormatBGRA8Unorm;

Page 14: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Create a RenderPipeline

MTLRenderPipelineDescriptor* desc = [MTLRenderPipelineDescriptor new]; !

// Set shaders id <MTLLibrary> library = [device newDefaultLibrary]; desc.vertexFunction = [library newFunctionWithName: @"myVertexShader"]; desc.fragmentFunction = [library newFunctionWithName: @“myFragmentShader"];

// Set framebuffer pixel format desc.colorAttachments[0].pixelFormat = MTLPixelFormatBGRA8Unorm;

// Compile the RenderPipelineState id <MTLRenderPipelineState> renderPipeline = [device newRenderPipelineStateWithDescriptor: desc error: &error];

Page 15: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Shader Input and Output

struct Vertex { float4 position; float4 color; }; !

struct VertexOut { float4 position [[position]]; float4 color; };

Page 16: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Shader Input and Output

struct Vertex { float4 position; float4 color; }; !

struct VertexOut { float4 position [[position]]; float4 color; };

Page 17: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

vertex VertexOut myVertexShader( const global Vertex* vertexArray [[ buffer(0) ]], unsigned int vid [[ vertex_id ]]) { VSOut out; out.position = vertexArray[vid].position; out.color = vertexArray[vid].color; return out; }

Vertex and Fragment Shaders

Page 18: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

vertex VertexOut myVertexShader( const global Vertex* vertexArray [[ buffer(0) ]], unsigned int vid [[ vertex_id ]]) { VSOut out; out.position = vertexArray[vid].position; out.color = vertexArray[vid].color; return out; }

Vertex and Fragment Shaders

Page 19: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

vertex VertexOut myVertexShader( const global Vertex* vertexArray [[ buffer(0) ]], unsigned int vid [[ vertex_id ]]) { VSOut out; out.position = vertexArray[vid].position; out.color = vertexArray[vid].color; return out; }

Vertex and Fragment Shaders

Page 20: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

vertex VertexOut myVertexShader( const global Vertex* vertexArray [[ buffer(0) ]], unsigned int vid [[ vertex_id ]]) { VSOut out; out.position = vertexArray[vid].position; out.color = vertexArray[vid].color; return out; }

Vertex and Fragment Shaders

Page 21: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

fragment float4 myFragmentShader( VertexOut interpolated [[stage_in]]) { return interpolated.color; }

vertex VertexOut myVertexShader( const global Vertex* vertexArray [[ buffer(0) ]], unsigned int vid [[ vertex_id ]]) { VSOut out; out.position = vertexArray[vid].position; out.color = vertexArray[vid].color; return out; }

Vertex and Fragment Shaders

Page 22: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

fragment float4 myFragmentShader( VertexOut interpolated [[stage_in]]) { return interpolated.color; }

vertex VertexOut myVertexShader( const global Vertex* vertexArray [[ buffer(0) ]], unsigned int vid [[ vertex_id ]]) { VSOut out; out.position = vertexArray[vid].position; out.color = vertexArray[vid].color; return out; }

Vertex and Fragment Shaders

Page 23: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

fragment float4 myFragmentShader( VertexOut interpolated [[stage_in]]) { return interpolated.color; }

vertex VertexOut myVertexShader( const global Vertex* vertexArray [[ buffer(0) ]], unsigned int vid [[ vertex_id ]]) { VSOut out; out.position = vertexArray[vid].position; out.color = vertexArray[vid].color; return out; }

Vertex and Fragment Shaders

Page 24: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

fragment float4 myFragmentShader( VertexOut interpolated [[stage_in]]) { return interpolated.color; }

vertex VertexOut myVertexShader( const global Vertex* vertexArray [[ buffer(0) ]], unsigned int vid [[ vertex_id ]]) { VSOut out; out.position = vertexArray[vid].position; out.color = vertexArray[vid].color; return out; }

Vertex and Fragment Shaders

Page 25: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Creating a Metal View

UIView Subclass CAMetalLayerUIViewController

Subclass

Page 26: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Creating a Metal View

@interface MyView : UIView @end !

@implementation MyView !

+ (id)layerClass { return [CAMetalLayer class]; } !

@end

Page 27: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Building a Metal ApplicationInitialization

1. Get the Device

2. Create a CommandQueue

3. Create Resources (Buffers and Textures)

4. Create RenderPipelineState

5. Create a View

Page 28: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Building a Metal ApplicationInitialization

1. Get the Device

2. Create a CommandQueue

3. Create Resources (Buffers and Textures)

4. Create RenderPipelineState

5. Create a View

Page 29: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Building a Metal ApplicationInitialization

1. Get the Device

2. Create a CommandQueue

3. Create Resources (Buffers and Textures)

4. Create RenderPipelineState

5. Create a View

Page 30: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Building a Metal ApplicationInitialization

1. Get the Device

2. Create a CommandQueue

3. Create Resources (Buffers and Textures)

4. Create RenderPipelineState

5. Create a View

Page 31: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Building a Metal ApplicationInitialization

1. Get the Device

2. Create a CommandQueue

3. Create Resources (Buffers and Textures)

4. Create RenderPipelineState

5. Create a View

Page 32: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Building a Metal ApplicationInitialization

1. Get the Device

2. Create a CommandQueue

3. Create Resources (Buffers and Textures)

4. Create RenderPipelineState

5. Create a View

Page 33: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Building a Metal ApplicationDrawing

1. Get a command buffer

2. Start a Render Pass

3. Draw

4. Commit the command buffer

Page 34: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Get a Command Buffer

// Get an available CommandBuffer commandBuffer = [queue commandBuffer];

Page 35: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Render Pass Configuration

MTLRenderPassDescriptor

Color Attachment 0

Color Attachment 1

Color Attachment 3

Depth Attachment

Stencil Attachment

Color Attachment 2

Page 36: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Render Pass Configuration

// Get this frame’s target drawable drawable = [metalLayer nextDrawable];

Page 37: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Render Pass Configuration

// Get this frame’s target drawable drawable = [metalLayer nextDrawable];

// Configure the Color0 Attachment renderDesc = [MTLRenderPassDescriptor new]; renderDesc.colorAttachments[0].texture = drawable.texture; renderDesc.colorAttachments[0].loadAction = MTLLoadActionClear; renderDesc.colorAttachments[0].clearValue = MTLClearValueMakeColor(…);

Page 38: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Render Pass Configuration

// Get this frame’s target drawable drawable = [metalLayer nextDrawable];

// Configure the Color0 Attachment renderDesc = [MTLRenderPassDescriptor new]; renderDesc.colorAttachments[0].texture = drawable.texture; renderDesc.colorAttachments[0].loadAction = MTLLoadActionClear; renderDesc.colorAttachments[0].clearValue = MTLClearValueMakeColor(…);

// Start a Render command id <MTLRenderCommandEncoder> render = [commandBuffer renderCommandEncoderWithDescriptor: renderDesc];

Page 39: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Drawing a Triangle

render = [commandBuffer renderCommandEncoderWithDescriptor: renderDesc]; [render setRenderPipelineState: renderPipeline]; [render setVertexBuffer: vertexArray offset: 0 atIndex: 0]; [render drawPrimitives: MTLPrimitiveTypeTriangle vertexStart:0 vertexCount:3]; [render endEncoding];

Page 40: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Committing a CommandBuffer

Page 41: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Committing a CommandBuffer

// Tell CoreAnimation when to present this drawable[commandBuffer addPresent: drawable];

Page 42: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Committing a CommandBuffer

// Tell CoreAnimation when to present this drawable[commandBuffer addPresent: drawable];// Put the command buffer into the queue[commandBuffer commit];

Page 43: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

1. Get a command buffer

2. Start a Render Pass

3. Draw

4. Commit the command buffer

Building a Metal ApplicationDrawing

Page 44: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

1. Get a command buffer

2. Start a Render Pass

3. Draw

4. Commit the command buffer

Building a Metal ApplicationDrawing

Page 45: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

1. Get a command buffer

2. Start a Render Pass

3. Draw

4. Commit the command buffer

Building a Metal ApplicationDrawing

Page 46: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

1. Get a command buffer

2. Start a Render Pass

3. Draw

4. Commit the command buffer

Building a Metal ApplicationDrawing

Page 47: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

1. Get a command buffer

2. Start a Render Pass

3. Draw

4. Commit the command buffer

Building a Metal ApplicationDrawing

Page 48: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Uniforms and Synchronization

Page 49: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer
Page 50: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer
Page 51: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Vertex Shader with Uniforms

struct Uniforms { float4x4 mvp_matrix; }; !

vertex VSOut vertexShader( const global Vertex* vertexArray [[ buffer(0) ]], constant Uniforms& uniforms [[ buffer(1) ]], unsigned int vid [[ vertex_id]]) { VSOut out; out.position = uniforms.mvp_matrix * vertexArray[vid].position; out.color = half4(vertexArray[vid].color); return out; }

Page 52: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Vertex Shader with Uniforms

struct Uniforms { float4x4 mvp_matrix; }; !

vertex VSOut vertexShader( const global Vertex* vertexArray [[ buffer(0) ]], constant Uniforms& uniforms [[ buffer(1) ]], unsigned int vid [[ vertex_id]]) { VSOut out; out.position = uniforms.mvp_matrix * vertexArray[vid].position; out.color = half4(vertexArray[vid].color); return out; }

Page 53: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Vertex Shader with Uniforms

struct Uniforms { float4x4 mvp_matrix; }; !

vertex VSOut vertexShader( const global Vertex* vertexArray [[ buffer(0) ]], constant Uniforms& uniforms [[ buffer(1) ]], unsigned int vid [[ vertex_id]]) { VSOut out; out.position = uniforms.mvp_matrix * vertexArray[vid].position; out.color = half4(vertexArray[vid].color); return out; }

Page 54: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Render Command with Uniforms

struct Uniforms* uniforms = [uniformBuffer contents]; uniforms->mvp_matrix = …; !

[render setRenderPipelineState: renderPipeline]; [render setVertexBuffer: vertexArray offset: 0 atIndex: 0]; [render setVertexBuffer: uniformBuffer offset: 0 atIndex: 1]; [render drawPrimitives:MTLPrimitiveTypeTriangle vertexStart:0 vertexCount:3];

Page 55: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Render Command with Uniforms

struct Uniforms* uniforms = [uniformBuffer contents]; uniforms->mvp_matrix = …; !

[render setRenderPipelineState: renderPipeline]; [render setVertexBuffer: vertexArray offset: 0 atIndex: 0]; [render setVertexBuffer: uniformBuffer offset: 0 atIndex: 1]; [render drawPrimitives:MTLPrimitiveTypeTriangle vertexStart:0 vertexCount:3];

Page 56: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

CPU and GPU Pipelining

CPU

GPU

Time

Page 57: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

CPU and GPU Pipelining

CPU

GPU

Uniform Buffer 1

Encode

Time

Page 58: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

CPU and GPU Pipelining

CPU

GPU

Uniform Buffer 1

Encode

Time

Execute

Page 59: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

CPU and GPU Pipelining

CPU

GPU

Uniform Buffer 1

Encode Encode

Time

Execute

Page 60: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

CPU and GPU Pipelining

CPU

GPU

Uniform Buffer 1 Uniform Buffer 2

Encode Encode

Execute

Time

Execute

Page 61: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

CPU and GPU Pipelining

CPU

GPU

Uniform Buffer 1 Uniform Buffer 2

Encode Encode

Execute

Time

Encode

Execute

Page 62: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

CPU and GPU Pipelining

CPU

GPU

Uniform Buffer 1 Uniform Buffer 2

Encode Encode

ExecuteExecute

Uniform Buffer 1

Time

Encode

Execute

Page 63: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

CPU and GPU Pipelining

CPU

GPU

Uniform Buffer 1 Uniform Buffer 2

Encode Encode

ExecuteExecute

Uniform Buffer 1

Time

Encode

Execute

Page 64: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

CPU and GPU Pipelining

CPU

GPU

Uniform Buffer 1 Uniform Buffer 2

Encode Encode

ExecuteExecute

Uniform Buffer 1

Time

Encode

Execute

Page 65: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

CPU and GPU Pipelining

CPU

GPU

Uniform Buffer 1 Uniform Buffer 2

Encode Encode

ExecuteExecute

Uniform Buffer 1

Time

EncodeWait

Execute

Page 66: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Waiting for Command Buffers

Page 67: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Waiting for Command Buffers

// Initialization available_resources = dispatch_semaphore_create(3);

Page 68: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Waiting for Command Buffers

// Initialization available_resources = dispatch_semaphore_create(3);

// Per frame { !

!

// Build a CommandBuffer !

!

!

!

!

[commandBuffer commit]; }

Page 69: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Waiting for Command Buffers

// Initialization available_resources = dispatch_semaphore_create(3);

// Per frame { !

!

// Build a CommandBuffer !

!

!

!

!

[commandBuffer commit]; }

dispatch_semaphore_wait(available_resources, DISPATCH_TIME_FOREVER);

Page 70: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Waiting for Command Buffers

// Initialization available_resources = dispatch_semaphore_create(3);

// Per frame { !

!

// Build a CommandBuffer !

!

!

!

!

[commandBuffer commit]; }

// Register a completion callback, unblock any waiting threads [commandBuffer addCompletedHandler:^(id<MTLCommandBuffer> cb) { dispatch_semaphore_signal(available_resources); }];

dispatch_semaphore_wait(available_resources, DISPATCH_TIME_FOREVER);

Page 71: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Metal Fundamentals

Building a Metal application • Initialization

• Drawing

• Uniforms and synchronization

Metal shading language • Writing shaders in Metal

• Data types in Metal

• Shader inputs, outputs, and matching rules

Page 72: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Metal Fundamentals

Building a Metal application • Initialization

• Drawing

• Uniforms and synchronization

Metal shading language • Writing shaders in Metal

• Data types in Metal

• Shader inputs, outputs, and matching rules

Page 73: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Metal Fundamentals

Building a Metal application • Initialization

• Drawing

• Uniforms and synchronization

Metal shading language • Writing shaders in Metal

• Data types in Metal

• Shader inputs, outputs, and matching rules

Page 74: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Metal Fundamentals

Building a Metal application • Initialization

• Drawing

• Uniforms and synchronization

Metal shading language • Writing shaders in Metal

• Data types in Metal

• Shader inputs, outputs, and matching rules

Page 75: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Metal Fundamentals

Building a Metal application • Initialization

• Drawing

• Uniforms and synchronization

Metal shading language • Writing shaders in Metal

• Data types in Metal

• Shader inputs, outputs, and matching rules

Page 76: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Metal Shading LanguageA unified language for graphics and compute

Aaftab Munshi GPU Software Engineer

Page 77: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Metal Fundamentals

Building a Metal application • Initialization

• Drawing

• Uniforms and synchronization

Metal shading language • Writing shaders in Metal

• Data types in Metal

• Shader inputs, outputs, and matching rules

Page 78: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Metal Fundamentals

Building a Metal application • Initialization

• Drawing

• Uniforms and synchronization

Metal shading language • Writing shaders in Metal

• Data types in Metal

• Shader inputs, outputs, and matching rules

Page 79: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Writing Shaders in Metal

Page 80: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

struct VertexOutput { float4 pos [[ position ]; float2 uv; };VertexOutputtexturedQuadVertex(const float4* vtx_data, const float2* uv_data, uint vid){ VertexOutput v_out; v_out.pos = vtx_data[vid]; v_out.uv = uv_data[vid]; return v_out; }

Pseudo Code for a Vertex Shader

Page 81: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

struct VertexOutput { float4 pos [[ position ]; float2 uv; };VertexOutputtexturedQuadVertex(const float4* vtx_data, const float2* uv_data, uint vid){ VertexOutput v_out; v_out.pos = vtx_data[vid]; v_out.uv = uv_data[vid]; return v_out; }

Pseudo Code for a Vertex Shader

Page 82: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Pseudo Code for a Vertex Shader

#include <metal_stdlib> using namespace metal; struct VertexOutput { float4 pos [[ position ]; float2 uv; }; VertexOutput texturedQuadVertex(const float4* vtx_data, const float2* uv_data, uint vid) { VertexOutput v_out; v_out.pos = vtx_data[vid]; v_out.uv = uv_data[vid]; return v_out; }

Page 83: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Pseudo Code for a Vertex Shader

#include <metal_stdlib> using namespace metal; struct VertexOutput { float4 pos [[ position ]; float2 uv; }; vertex VertexOutput texturedQuadVertex(const float4* vtx_data, const float2* uv_data, uint vid) { VertexOutput v_out; v_out.pos = vtx_data[vid]; v_out.uv = uv_data[vid]; return v_out; }

Page 84: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Pseudo Code for a Vertex Shader

#include <metal_stdlib> using namespace metal; struct VertexOutput { float4 pos [[ position ]; float2 uv; }; vertex VertexOutput texturedQuadVertex(const global float4* vtx_data, [[ buffer(0) ]], const global float2* uv_data, [[ buffer(1) ]], uint vid) { VertexOutput v_out; v_out.pos = vtx_data[vid]; v_out.uv = uv_data[vid]; return v_out; }

Page 85: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Metal Vertex Shader

#include <metal_stdlib> using namespace metal; struct VertexOutput { float4 pos [[ position ]; float2 uv; }; vertex VertexOutput texturedQuadVertex(const global float4* vtx_data, [[ buffer(0) ]], const global float2* uv_data, [[ buffer(1) ]], uint vid [[ vertex_id ]]) { VertexOutput v_out; v_out.pos = vtx_data[vid]; v_out.uv = uv_data[vid]; return v_out; }

Page 86: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Metal Vertex Shader

#include <metal_stdlib> using namespace metal; struct VertexOutput { float4 pos [[ position ]; float2 uv; }; vertex VertexOutput texturedQuadVertex(const global float4* vtx_data, [[ buffer(0) ]], const global float2* uv_data, [[ buffer(1) ]], uint vid [[ vertex_id ]]) { VertexOutput v_out; v_out.pos = vtx_data[vid]; v_out.uv = uv_data[vid]; return v_out; }

Page 87: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Pseudo Code for a Fragment Shader

#include <metal_stdlib> using namespace metal; struct VertexOutput { float4 pos [[ position ]; float2 uv; }; float4 texturedQuadFragment(VertexOutput frag_input, texture2d<float> tex [[ texture(0) ]], sampler s [[ sampler(0) ]] { return tex.sample(s, frag_input.uv); }

Page 88: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Pseudo Code for a Fragment Shader

#include <metal_stdlib> using namespace metal; struct VertexOutput { float4 pos [[ position ]; float2 uv; }; fragment float4 texturedQuadFragment(VertexOutput frag_input, texture2d<float> tex [[ texture(0) ]], sampler s [[ sampler(0) ]] { return tex.sample(s, frag_input.uv); }

Page 89: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Metal Fragment Shader

#include <metal_stdlib> using namespace metal; struct VertexOutput { float4 pos [[ position ]; float2 uv; }; fragment float4 texturedQuadFragment(VertexOutput frag_input, [[ stage_in ]], texture2d<float> tex [[ texture(0) ]], sampler s [[ sampler(0) ]] { return tex.sample(s, frag_input.uv); }

Page 90: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Metal Fragment Shader

#include <metal_stdlib> using namespace metal; struct VertexOutput { float4 pos [[ position ]; float2 uv; }; fragment float4 texturedQuadFragment(VertexOutput frag_input, [[ stage_in ]], texture2d<float> tex [[ texture(0) ]], sampler s [[ sampler(0) ]] { return tex.sample(s, frag_input.uv); }

Page 91: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Data TypesScalars, vectors, matrices, and atomics

Page 92: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Scalars

Page 93: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Scalars

C++11 scalar types

Page 94: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Scalars

C++11 scalar types

The half type

Page 95: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Scalars

C++11 scalar types

The half type

Use the half type wherever you can

Page 96: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Vectors and MatricesMore than just a big scalar

Page 97: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Vectors and MatricesMore than just a big scalar

Vectors • Two-, three-, and four-component integer and floating-point types

• char2, int3, float4, half2, etc.

Page 98: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Vectors and MatricesMore than just a big scalar

Vectors • Two-, three-, and four-component integer and floating-point types

• char2, int3, float4, half2, etc.

Matrices • floatnxm, halfnxm

• Column major order

Page 99: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Vectors and MatricesMore than just a big scalar

Vectors • Two-, three-, and four-component integer and floating-point types

• char2, int3, float4, half2, etc.

Matrices • floatnxm, halfnxm

• Column major order

Vector and Matrix Constructors and Operators • Similar to GLSL

Page 100: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Vectors and MatricesMore than just a big scalar

Vectors • Two-, three-, and four-component integer and floating-point types

• char2, int3, float4, half2, etc.

Matrices • floatnxm, halfnxm

• Column major order

Vector and Matrix Constructors and Operators • Similar to GLSL

Types defined by simd/simd.h

Page 101: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Vectors and MatricesMore than just a big scalar

Vectors • Two-, three-, and four-component integer and floating-point types

• char2, int3, float4, half2, etc.

Matrices • floatnxm, halfnxm

• Column major order

Vector and Matrix Constructors and Operators • Similar to GLSL

Types defined by simd/simd.hUse the halfn and halfnxm types wherever you can

Page 102: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

VectorsAligned at vector length

struct Foo { float a; float2 b; float4 c;};

Page 103: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

VectorsAligned at vector length

struct Foo { float a; float2 b; float4 c;};

alignment = 8 bytes

Page 104: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

VectorsAligned at vector length

struct Foo { float a; float2 b; float4 c;};

alignment = 8 bytesalignment = 16 bytes

Page 105: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Potential impact to both allocation size and memory b/w

VectorsAligned at vector length

struct Foo { float a; float pad; float2 b; float4 c; };

Page 106: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Potential impact to both allocation size and memory b/w

VectorsAligned at vector length

struct Foo { float a; float pad; float2 b; float4 c; };

generated by compiler

Page 107: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Potential impact to both allocation size and memory b/w

VectorsAligned at vector length

struct Foo { float a; float pad; float2 b; float4 c; };

sizeof(Foo) = 32 bytes

generated by compiler

Page 108: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

VectorsAligned at vector length

struct Foo { float4 c; float2 b; float a; };

What if we declare them in order of decreasing size?

Page 109: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

VectorsAligned at vector length

struct Foo { float4 c; float2 b; float a; };

sizeof(Foo) is still 32 bytes

What if we declare them in order of decreasing size?

Page 110: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

VectorsPacked vector types

Page 111: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

VectorsPacked vector types

packed_float3, packed_char4, …

Page 112: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

VectorsPacked vector types

packed_float3, packed_char4, …

Always aligned at scalar type length

Page 113: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

VectorsPacked vector types

packed_float3, packed_char4, …

Always aligned at scalar type length

struct Foo { float a; packed_float2 b; packed_float4 c; };

Page 114: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

VectorsPacked vector types

packed_float3, packed_char4, …

Always aligned at scalar type length

struct Foo { float a; packed_float2 b; packed_float4 c; };

alignment = 4 bytesalignment = 4 bytes

Page 115: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

VectorsPacked vector types

packed_float3, packed_char4, …

Always aligned at scalar type length

struct Foo { float a; packed_float2 b; packed_float4 c; };

sizeof(Foo) = 28 bytes

alignment = 4 bytesalignment = 4 bytes

Page 116: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

VectorsPacked vector types

packed_float3, packed_char4, …

Always aligned at scalar type length

struct Foo { float a; packed_float2 b; packed_float4 c; };

sizeof(Foo) = 28 bytes

alignment = 4 bytesalignment = 4 bytes

Not a good fit for CPU as CPUs prefer aligned vector types

Page 117: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Atomic

Page 118: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Atomic

Supported atomic types • atomic_int and atomic_uint

Page 119: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Atomic

Supported atomic types • atomic_int and atomic_uint

Operations on atomic types are race-free • Subset of C++11 atomic functions

• Guaranteed to be performed without interference from other threads

Page 120: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Data TypesTextures, samplers, and buffers

Page 121: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

TexturesA templated type

Page 122: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Template parameters

TexturesA templated type

Page 123: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Template parameters• Color type

- Float, half, int, or uint

TexturesA templated type

Page 124: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Template parameters• Color type

- Float, half, int, or uint

• Access mode

- Sample, read, or write

TexturesA templated type

Page 125: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Template parameters• Color type

- Float, half, int, or uint

• Access mode

- Sample, read, or write

Separate type for depth textures

TexturesA templated type

Page 126: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

fragment FragOutput my_fragment_shader( texture2d<float> tA [[ texture(0) ]], texture2d<half, access::write> tB [[ texture(1) ]], depth2d<float> tC [[ texture(2) ]], …) {}

TexturesA templated type

Page 127: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

fragment FragOutput my_fragment_shader( texture2d<float> tA [[ texture(0) ]], texture2d<half, access::write> tB [[ texture(1) ]], depth2d<float> tC [[ texture(2) ]], …) {}

TexturesA templated type

Page 128: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

fragment FragOutput my_fragment_shader( texture2d<float> tA [[ texture(0) ]], texture2d<half, access::write> tB [[ texture(1) ]], depth2d<float> tC [[ texture(2) ]], …) {}

TexturesA templated type

Page 129: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

fragment FragOutput my_fragment_shader( texture2d<float> tA [[ texture(0) ]], texture2d<half, access::write> tB [[ texture(1) ]], depth2d<float> tC [[ texture(2) ]], …) {}

TexturesA templated type

Page 130: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

SamplersSamplers independent from textures

Page 131: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

One sampler, multiple textures

SamplersSamplers independent from textures

Sampler

Page 132: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

One sampler, multiple textures Multiple samplers, one texture

SamplersSamplers independent from textures

Sampler Sampler A Sampler B

Page 133: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

fragment float4 texturedQuadFragment(VertexOutput frag_input [[ stage_in ]], texture2d<float> tex [[ texture(0) ]], sampler s [[ sampler(0) ]]) { return tex.sample(s, frag_input.texcoord); }

SamplersArgument to a graphics or kernel function

Page 134: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

fragment float4 texturedQuadFragment(VertexOutput frag_input [[ stage_in ]], texture2d<float> tex [[ texture(0) ]], sampler s [[ sampler(0) ]]) { return tex.sample(s, frag_input.texcoord); }

SamplersArgument to a graphics or kernel function

Page 135: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

SamplersDeclared in Metal source

Page 136: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

SamplersDeclared in Metal source

// Defined as a variadic templateconstexpr sampler s(coord::normalized, filter::linear, address::clamp_to_edge);

Page 137: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

SamplersDeclared in Metal source

// Defined as a variadic templateconstexpr sampler s(coord::normalized, filter::linear, address::clamp_to_edge);

// Defaults for sampler properties not specifiedconstexpr sampler s(address::clamp_to_zero);

Page 138: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

BuffersShow me the memory

Page 139: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

BuffersShow me the memory

A pointer or a reference to a type

Page 140: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

BuffersShow me the memory

A pointer or a reference to a type

Must be declared in an address space • global

• constant

Page 141: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

BuffersWhen to use global

Page 142: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

BuffersWhen to use global

When buffers are indexed dynamically such as with: • vertex ID

• global ID

Page 143: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

BuffersWhen to use constant

Page 144: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

BuffersWhen to use constant

Should be used when multiple instances index the same location

Page 145: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

BuffersWhen to use constant

Should be used when multiple instances index the same location

For data structures such as:

• Light descriptors, material properties

• Skinning matrices

• Filter weights

Page 146: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

BuffersWhen to use constant

Should be used when multiple instances index the same location

For data structures such as:

• Light descriptors, material properties

• Skinning matrices

• Filter weights

Pass by reference

Page 147: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Global vs. ConstantExample

float3* position_data [[ buffer(0) ]],float3* normal_data [[ buffer(1) ]],

vertex VertexOutput my_vertex(const const uint vid [[ vertex_id ]]) { VertexOutput out; float3 n_d = normal_data[vid]; float3 transformed_normal = matrices.normal_matrix * n_d; float4 p_d = float4(position_data[vid], 1.0f); out.position = matrices.modelview_projection_matrix * p_d; float4 eye_vector = matrices.modelview_matrix * p_d; ... return out;}

TransformMatrices& matrices [[ buffer(2) ]],

Page 148: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Global vs. ConstantExample

float3* position_data [[ buffer(0) ]],float3* normal_data [[ buffer(1) ]],

vertex VertexOutput my_vertex(const const uint vid [[ vertex_id ]]) { VertexOutput out; float3 n_d = normal_data[vid]; float3 transformed_normal = matrices.normal_matrix * n_d; float4 p_d = float4(position_data[vid], 1.0f); out.position = matrices.modelview_projection_matrix * p_d; float4 eye_vector = matrices.modelview_matrix * p_d; ... return out;}

TransformMatrices& matrices [[ buffer(2) ]],

Page 149: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Global vs. ConstantExample

float3* position_data [[ buffer(0) ]],float3* normal_data [[ buffer(1) ]],

vertex VertexOutput my_vertex(const const uint vid [[ vertex_id ]]) { VertexOutput out; float3 n_d = normal_data[vid]; float3 transformed_normal = matrices.normal_matrix * n_d; float4 p_d = float4(position_data[vid], 1.0f); out.position = matrices.modelview_projection_matrix * p_d; float4 eye_vector = matrices.modelview_matrix * p_d; ... return out;}

TransformMatrices& matrices [[ buffer(2) ]],

Page 150: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Global vs. ConstantExample

float3* position_data [[ buffer(0) ]],float3* normal_data [[ buffer(1) ]],

vertex VertexOutput my_vertex(const const uint vid [[ vertex_id ]]) { VertexOutput out; float3 n_d = normal_data[vid]; float3 transformed_normal = matrices.normal_matrix * n_d; float4 p_d = float4(position_data[vid], 1.0f); out.position = matrices.modelview_projection_matrix * p_d; float4 eye_vector = matrices.modelview_matrix * p_d; ... return out;}

globalglobal

TransformMatrices& matrices [[ buffer(2) ]],

Page 151: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Global vs. ConstantExample

float3* position_data [[ buffer(0) ]],float3* normal_data [[ buffer(1) ]],

vertex VertexOutput my_vertex(const const uint vid [[ vertex_id ]]) { VertexOutput out; float3 n_d = normal_data[vid]; float3 transformed_normal = matrices.normal_matrix * n_d; float4 p_d = float4(position_data[vid], 1.0f); out.position = matrices.modelview_projection_matrix * p_d; float4 eye_vector = matrices.modelview_matrix * p_d; ... return out;}

globalglobal

TransformMatrices& matrices [[ buffer(2) ]],

Page 152: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Global vs. ConstantExample

constant

float3* position_data [[ buffer(0) ]],float3* normal_data [[ buffer(1) ]],

vertex VertexOutput my_vertex(const const uint vid [[ vertex_id ]]) { VertexOutput out; float3 n_d = normal_data[vid]; float3 transformed_normal = matrices.normal_matrix * n_d; float4 p_d = float4(position_data[vid], 1.0f); out.position = matrices.modelview_projection_matrix * p_d; float4 eye_vector = matrices.modelview_matrix * p_d; ... return out;}

globalglobal

TransformMatrices& matrices [[ buffer(2) ]],

Page 153: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Per-Vertex InputsTwo methods for reading vertex data

Page 154: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Per-Vertex Inputs—Option OneVertex data layout is known by the shader

Page 155: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Per-Vertex Inputs—Option OneVertex data layout is known by the shader

Pass pointers to vertex input buffers in global address space

Use vertex ID and instance ID to index into vertex buffers

Page 156: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Per-Vertex Inputs—Option OneVertex data layout is known by the shader

Pass pointers to vertex input buffers in global address space

Use vertex ID and instance ID to index into vertex buffers

vertex VertexOutputmy_vertex_shader(vertexInputA* inputA [[ buffer(0) ]], vertexInputB* inputB [[ buffer(1) ]], uint vid [[ vertex_id ]], uint instid [[ instance_id ]]) { float a = inputA[vid].a; half4 b = inputB[instid].b; ... }

Page 157: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Per-Vertex Inputs—Option OneVertex data layout is known by the shader

Pass pointers to vertex input buffers in global address space

Use vertex ID and instance ID to index into vertex buffers

vertex VertexOutputmy_vertex_shader(vertexInputA* inputA [[ buffer(0) ]], vertexInputB* inputB [[ buffer(1) ]], uint vid [[ vertex_id ]], uint instid [[ instance_id ]]) { float a = inputA[vid].a; half4 b = inputB[instid].b; ... }

Page 158: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Per-Vertex Inputs—Option TwoDecouple vertex input data from type used in shader

Page 159: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Per-Vertex Inputs—Option TwoDecouple vertex input data from type used in shader

Good match to OpenGL’s Vertex Array API

Page 160: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Per-Vertex Inputs—Option TwoDecouple vertex input data from type used in shader

Good match to OpenGL’s Vertex Array API

A vertex descriptor for fetching data in the API • Data type in shader can be different from the input data format

• One or more buffers can be used to describe vertex inputs

Page 161: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Per-Vertex Inputs—Option TwoDecouple vertex input data from type used in shader

Good match to OpenGL’s Vertex Array API

A vertex descriptor for fetching data in the API • Data type in shader can be different from the input data format

• One or more buffers can be used to describe vertex inputs

Per-vertex inputs to shader • Declared as a struct

• Described with the [[ stage_in ]] qualifier

Page 162: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Per-Vertex Inputs—Option TwoDecouple vertex input data from type used in shader

Good match to OpenGL’s Vertex Array API

A vertex descriptor for fetching data in the API • Data type in shader can be different from the input data format

• One or more buffers can be used to describe vertex inputs

Per-vertex inputs to shader • Declared as a struct

• Described with the [[ stage_in ]] qualifier

Attribute index to identify each vertex input

Page 163: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Per-Vertex Inputs—Option 2Decouple vertex input data from type used in shader

Attribute Argument Table

Page 164: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Per-Vertex Inputs—Option 2Decouple vertex input data from type used in shader

Attribute Argument Table

Index 0position

0 12

Page 165: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Per-Vertex Inputs—Option 2Decouple vertex input data from type used in shader

Attribute Argument Table

Index 0

Index 1

positionnormal

0 12 24

Page 166: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Per-Vertex Inputs—Option 2Decouple vertex input data from type used in shader

Attribute Argument Table

Index 0

Index 1

Index 2

positionnormalcolor

0 12 24 28

Page 167: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Per-Vertex Inputs—Option 2Decouple vertex input data from type used in shader

Attribute Argument Table

Index 0

Index 1

Index 2

Index 3

positionnormalcolortexcoord

0 12 24 28 32

Page 168: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Per-Vertex Inputs—Option 2Specifying vertex attribute indices in a shader

struct VertexInput { float4 position [[ attribute(0) ]]; float3 normal [[ attribute(1) ]]; half4 color [[ attribute(2) ]]; half2 texcoord [[ attribute(3) ]]; }; vertex VertexOutputmy_vertex_shader(VertexInput v_in [[ stage_in ]], …)

Page 169: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Per-Vertex Inputs—Option 2Specifying vertex attribute indices in a shader

struct VertexInput { float4 position [[ attribute(0) ]]; float3 normal [[ attribute(1) ]]; half4 color [[ attribute(2) ]]; half2 texcoord [[ attribute(3) ]]; }; vertex VertexOutputmy_vertex_shader(VertexInput v_in [[ stage_in ]], …)

Page 170: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

MTLVertexDescriptor* vertexDesc = [[MTLVertexDescriptor alloc] init];[vertexDesc setVertexFormat:MTLVertexFormatFloat3 offset:0 vertexBufferIndex:0 atAttributeIndex:0]

Per-Vertex Inputs—Option 2Building the vertex descriptor

Page 171: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

MTLVertexDescriptor* vertexDesc = [[MTLVertexDescriptor alloc] init];[vertexDesc setVertexFormat:MTLVertexFormatFloat3 offset:0 vertexBufferIndex:0 atAttributeIndex:0]

Per-Vertex Inputs—Option 2Building the vertex descriptor

Page 172: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

MTLVertexDescriptor* vertexDesc = [[MTLVertexDescriptor alloc] init];[vertexDesc setVertexFormat:MTLVertexFormatFloat3 offset:0 vertexBufferIndex:0 atAttributeIndex:0]

Per-Vertex Inputs—Option 2Building the vertex descriptor

Page 173: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

MTLVertexDescriptor* vertexDesc = [[MTLVertexDescriptor alloc] init];[vertexDesc setVertexFormat:MTLVertexFormatFloat3 offset:0 vertexBufferIndex:0 atAttributeIndex:0]

Per-Vertex Inputs—Option 2Building the vertex descriptor

Page 174: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

MTLVertexDescriptor* vertexDesc = [[MTLVertexDescriptor alloc] init];[vertexDesc setVertexFormat:MTLVertexFormatFloat3 offset:0 vertexBufferIndex:0 atAttributeIndex:0]

Per-Vertex Inputs—Option 2Building the vertex descriptor

Page 175: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

MTLVertexDescriptor* vertexDesc = [[MTLVertexDescriptor alloc] init];[vertexDesc setVertexFormat:MTLVertexFormatFloat3 offset:0 vertexBufferIndex:0 atAttributeIndex:0][vertexDesc setVertexFormat:MTLVertexFormatFloat3 offset:12 vertexBufferIndex:0 atAttributeIndex:1]

Per-Vertex Inputs—Option 2Building the vertex descriptor

Page 176: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

MTLVertexDescriptor* vertexDesc = [[MTLVertexDescriptor alloc] init];[vertexDesc setVertexFormat:MTLVertexFormatFloat3 offset:0 vertexBufferIndex:0 atAttributeIndex:0][vertexDesc setVertexFormat:MTLVertexFormatFloat3 offset:12 vertexBufferIndex:0 atAttributeIndex:1][vertexDesc setVertexFormat:MTLVertexFormatUChar4Normalized offset:24 vertexBufferIndex:0 atAttributeIndex:2]

Per-Vertex Inputs—Option 2Building the vertex descriptor

Page 177: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

MTLVertexDescriptor* vertexDesc = [[MTLVertexDescriptor alloc] init];[vertexDesc setVertexFormat:MTLVertexFormatFloat3 offset:0 vertexBufferIndex:0 atAttributeIndex:0][vertexDesc setVertexFormat:MTLVertexFormatFloat3 offset:12 vertexBufferIndex:0 atAttributeIndex:1][vertexDesc setVertexFormat:MTLVertexFormatUChar4Normalized offset:24 vertexBufferIndex:0 atAttributeIndex:2][vertexDesc setVertexFormat:MTLVertexFormatUShort2Normalized offset:28 vertexBufferIndex:0 atAttributeIndex:3];

Per-Vertex Inputs—Option 2Building the vertex descriptor

Page 178: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

MTLVertexDescriptor* vertexDesc = [[MTLVertexDescriptor alloc] init];[vertexDesc setVertexFormat:MTLVertexFormatFloat3 offset:0 vertexBufferIndex:0 atAttributeIndex:0][vertexDesc setVertexFormat:MTLVertexFormatFloat3 offset:12 vertexBufferIndex:0 atAttributeIndex:1][vertexDesc setVertexFormat:MTLVertexFormatUChar4Normalized offset:24 vertexBufferIndex:0 atAttributeIndex:2][vertexDesc setVertexFormat:MTLVertexFormatUShort2Normalized offset:28 vertexBufferIndex:0 atAttributeIndex:3];[vertexDesc setStride:32 atVertexBufferIndex:0];

Per-Vertex Inputs—Option 2Building the vertex descriptor

Page 179: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

MTLVertexDescriptor* vertexDesc = [[MTLVertexDescriptor alloc] init];[vertexDesc setVertexFormat:MTLVertexFormatFloat3 offset:0 vertexBufferIndex:0 atAttributeIndex:0][vertexDesc setVertexFormat:MTLVertexFormatFloat3 offset:12 vertexBufferIndex:0 atAttributeIndex:1][vertexDesc setVertexFormat:MTLVertexFormatUChar4Normalized offset:24 vertexBufferIndex:0 atAttributeIndex:2][vertexDesc setVertexFormat:MTLVertexFormatUShort2Normalized offset:28 vertexBufferIndex:0 atAttributeIndex:3];[vertexDesc setStride:32 atVertexBufferIndex:0];// add vertex descriptor to the MTLRenderPipelineDescriptorpipelineDescriptor.vertexDescriptor = vertexDesc;

Per-Vertex Inputs—Option 2Building the vertex descriptor

Page 180: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Per-Vertex OutputsTwo methods for writing vertex data

Page 181: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Per-Vertex OutputsReturn type of vertex shader

Page 182: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Per-Vertex OutputsReturn type of vertex shader

A float4 or a user-defined struct

Page 183: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Per-Vertex OutputsReturn type of vertex shader

A float4 or a user-defined struct

Elements of a user-defined struct

Page 184: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Per-Vertex OutputsReturn type of vertex shader

A float4 or a user-defined struct

Elements of a user-defined struct• A scalar, vector, or matrix type

Page 185: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Per-Vertex OutputsReturn type of vertex shader

A float4 or a user-defined struct

Elements of a user-defined struct• A scalar, vector, or matrix type

• Built-in variables[[ position ]][[ point_size ]][[ clip_distance ]]

Page 186: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Per-Vertex OutputsReturn type of vertex shader

A float4 or a user-defined struct

Elements of a user-defined struct• A scalar, vector, or matrix type

• Built-in variables[[ position ]][[ point_size ]][[ clip_distance ]]

• Position must always be returned

Page 187: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Per-Vertex OutputsReturn type of vertex shader

struct VertexOutput { float4 pos [[ position ]]; half4 color; float pt [[ point_size ]]; float2 texcoord;} vertex VertexOutputmy_vertex_shaderA(...){}

Page 188: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Per-Vertex OutputsAnyway you want, just the way you need…to write

Page 189: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Per-Vertex OutputsAnyway you want, just the way you need…to write

Output to a buffer(s) using your vertex ID

Page 190: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Per-Vertex OutputsAnyway you want, just the way you need…to write

Output to a buffer(s) using your vertex IDstruct VertexOutput { float4 pos; half4 color; float2 texcoord;};vertex void my_vertex_shaderA(global VertexOutput* output_buffer [[ buffer(0) ]], uint vid [[ vertex_id ]], ...){ VertexOutput v_out; ... output_buffer[vid] = v_out;}

Page 191: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Per-Vertex OutputsAnyway you want, just the way you need…to write

Output to a buffer(s) using your vertex IDstruct VertexOutput { float4 pos; half4 color; float2 texcoord;};vertex void my_vertex_shaderA(global VertexOutput* output_buffer [[ buffer(0) ]], uint vid [[ vertex_id ]], ...){ VertexOutput v_out; ... output_buffer[vid] = v_out;}

Page 192: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Per-Vertex OutputsAnyway you want, just the way you need…to write

Output to a buffer(s) using your vertex IDstruct VertexOutput { float4 pos; half4 color; float2 texcoord;};vertex void my_vertex_shaderA(global VertexOutput* output_buffer [[ buffer(0) ]], uint vid [[ vertex_id ]], ...){ VertexOutput v_out; ... output_buffer[vid] = v_out;}

Page 193: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Per-Vertex OutputsAnyway you want, just the way you need…to write

Output to a buffer(s) using your vertex IDstruct VertexOutput { float4 pos; half4 color; float2 texcoord;};vertex void my_vertex_shaderA(global VertexOutput* output_buffer [[ buffer(0) ]], uint vid [[ vertex_id ]], ...){ VertexOutput v_out; ... output_buffer[vid] = v_out;}

Page 194: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Per-Vertex OutputsAnyway you want, just the way you need…to write

Output to a buffer(s) using your vertex IDstruct VertexOutput { float4 pos; half4 color; float2 texcoord;};vertex void my_vertex_shaderA(global VertexOutput* output_buffer [[ buffer(0) ]], uint vid [[ vertex_id ]], ...){ VertexOutput v_out; ... output_buffer[vid] = v_out;}

Page 195: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Per-FragmentInputs and outputs

Page 196: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Per-Fragment InputsOutput of a vertex shader

Page 197: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Per-Fragment InputsOutput of a vertex shader

Declared with the [[ stage_in ]] qualifier

Page 198: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Per-Fragment InputsOutput of a vertex shader

Declared with the [[ stage_in ]] qualifier

Built-in variables generated by the rasterizer • Front facing

• Point coordinate

• Sample ID and sample mask

Page 199: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Per-Fragment InputsOutput of a vertex shader

Declared with the [[ stage_in ]] qualifier

Built-in variables generated by the rasterizer • Front facing

• Point coordinate

• Sample ID and sample mask

Frame-buffer color values • For programmable blending

Page 200: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Per-Fragment InputsOutput of a vertex shader

struct MyFragmentInput { half3 normal; float2 texcoord;}; fragment float4my_fragment_shader( MyFragmentInput fragIn [[ stage_in ]], bool is_front_face [[ front_facing ]], half4 fb_color [[ color(0) ]]) { ... }

Page 201: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Per-Fragment InputsOutput of a vertex shader

struct MyFragmentInput { half3 normal; float2 texcoord;}; fragment float4my_fragment_shader( MyFragmentInput fragIn [[ stage_in ]], bool is_front_face [[ front_facing ]], half4 fb_color [[ color(0) ]]) { ... }

Page 202: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Per-Fragment InputsOutput of a vertex shader

struct MyFragmentInput { half3 normal; float2 texcoord;}; fragment float4my_fragment_shader( MyFragmentInput fragIn [[ stage_in ]], bool is_front_face [[ front_facing ]], half4 fb_color [[ color(0) ]]) { ... }

Page 203: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Per-Fragment InputsOutput of a vertex shader

struct MyFragmentInput { half3 normal; float2 texcoord;}; fragment float4my_fragment_shader( MyFragmentInput fragIn [[ stage_in ]], bool is_front_face [[ front_facing ]], half4 fb_color [[ color(0) ]]) { ... }

Page 204: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Per-Fragment InputsOutput of a vertex shader

struct MyFragmentInput { half3 normal; float2 texcoord;}; fragment float4my_fragment_shader( MyFragmentInput fragIn [[ stage_in ]], bool is_front_face [[ front_facing ]], half4 fb_color [[ color(0) ]]) { ... }

Page 205: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Per-Fragment InputsOutput of a vertex shader

struct MyFragmentInput { half3 normal; float2 texcoord;}; fragment float4my_fragment_shader( MyFragmentInput fragIn [[ stage_in ]], bool is_front_face [[ front_facing ]], half4 fb_color [[ color(0) ]]) { ... }

Page 206: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Per-Fragment InputsOutput of a vertex shader

struct MyFragmentInput { half3 normal; float2 texcoord;}; fragment float4my_fragment_shader( MyFragmentInput fragIn [[ stage_in ]], bool is_front_face [[ front_facing ]], half4 fb_color [[ color(0) ]]) { ... }

Page 207: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Per-Fragment OutputsReturn type of fragment shader

Page 208: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Per-Fragment OutputsReturn type of fragment shader

A scalar, vector, or user-defined struct

Page 209: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Per-Fragment OutputsReturn type of fragment shader

A scalar, vector, or user-defined struct

Color, depth, or sample mask

Page 210: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Per-Fragment OutputsReturn type of fragment shader

A scalar, vector, or user-defined struct

Color, depth, or sample mask

Identified with attributes • [[ color(m) ]]

• [[ depth(qualifier) ]]

• [[ sample_mask ]]

Page 211: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Per-Fragment OutputsReturn type of fragment shader

Page 212: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Per-Fragment OutputsReturn type of fragment shader

fragment float4 my_fragment_shader(…)

Page 213: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Per-Fragment OutputsReturn type of fragment shader

fragment float4 my_fragment_shader(…)

struct MyFragmentOutput { half4 clrA [[ color(0) ]]; int4 clrB [[ color(2) ]]; uint4 clrC [[ color(1) ]]; }; fragment MyFragmentOutputmy_fragment_shader(…){ MyFragmentOutput v; ... return v;}

Page 214: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Shader Signature MatchingA match made in heaven

Page 215: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Shader Signature MatchingTypes match

Page 216: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Shader Signature MatchingTypes match

struct VertexOutput { float4 pos [[ position ]]; float3 normal; float2 texcoord;};

Page 217: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Shader Signature MatchingTypes match

struct VertexOutput { float4 pos [[ position ]]; float3 normal; float2 texcoord;};

vertex VertexOutput my_vertex_shader(…){ VertexOutput v; ... return v;}

fragment float4 my_fragment_shader(VertexOutput frag_in [[ stage_in ]],…) { float4 f; ... return f;}

Page 218: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Shader Signature MatchingFlexible pairing

struct VertexOutput { float4 pos [[ position ]]; float3 normal [[ user(N)]]; float2 texcoord [[ user(T) ]]; };

struct FragmentInput { float4 pos [[ position ]]; float2 texcoord [[ user(T) ]]; };

Page 219: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Shader Signature MatchingFlexible pairing

struct VertexOutput { float4 pos [[ position ]]; float3 normal [[ user(N)]]; float2 texcoord [[ user(T) ]]; };

struct FragmentInput { float4 pos [[ position ]]; float2 texcoord [[ user(T) ]]; };

Page 220: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Shader Signature MatchingFlexible pairing

struct VertexOutput { float4 pos [[ position ]]; float3 normal [[ user(N)]]; float2 texcoord [[ user(T) ]]; };

struct FragmentInput { float4 pos [[ position ]]; float2 texcoord [[ user(T) ]]; };

Page 221: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Shader Signature MatchingFlexible pairing

struct VertexOutput { float4 pos [[ position ]]; float3 normal [[ user(N)]]; float2 texcoord [[ user(T) ]]; };

vertex VertexOutput my_vertex_shader(…){ VertexOutput v; ... return v;}

fragment float4 my_fragment_shader(FragmentInput frag_in [[ stage_in ]],…) { float4 f; ... return f;}

struct FragmentInput { float4 pos [[ position ]]; float2 texcoord [[ user(T) ]]; };

Page 222: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Math in ShadersFast or precise, maybe both

Page 223: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Math

Page 224: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Math

By default, all math operations in fast mode

Page 225: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Math

By default, all math operations in fast mode

Why would you want to choose precise mode?

Page 226: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Math

By default, all math operations in fast mode

Why would you want to choose precise mode?• Handling of NaNs is undefined in fast mode

- e.g., how should clamp (NaN, min, max) behave?

Page 227: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Math

By default, all math operations in fast mode

Why would you want to choose precise mode?• Handling of NaNs is undefined in fast mode

- e.g., how should clamp (NaN, min, max) behave?

• Math functions only operate over a limited range in fast mode

Page 228: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Math

By default, all math operations in fast mode

Why would you want to choose precise mode?• Handling of NaNs is undefined in fast mode

- e.g., how should clamp (NaN, min, max) behave?

• Math functions only operate over a limited range in fast mode

Compiler option -fno-fast-math to change default to precise math

Page 229: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Math

By default, all math operations in fast mode

Why would you want to choose precise mode?• Handling of NaNs is undefined in fast mode

- e.g., how should clamp (NaN, min, max) behave?

• Math functions only operate over a limited range in fast mode

Compiler option -fno-fast-math to change default to precise math• Be careful as this may impact performance of your shader

Page 230: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

MathPrecise math in fast mode

Page 231: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

MathPrecise math in fast mode

Nested name spaces—metal::precise and metal::fast

Page 232: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

MathPrecise math in fast mode

Nested name spaces—metal::precise and metal::fast

Use explicit math function name • precise::clamp, precise::sin

Page 233: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Metal Standard LibraryQuite a nice list of functions if I do say so myself

Page 234: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Metal Standard Library Functions

Page 235: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Metal Standard Library Functions

Common Functions T clamp(T x, T minval, T maxval) T mix(T x, T y, T a) T saturate(T x) T sign(T x) T smoothstep(T edge0, T edge1, T x) T step(T edge, T x) Integer Functions T abs(T x) Tu absdiff(T x, T y) T addsat(T x, T y) T clamp(T x, T minval, T maxval) T clz(T x) T ctz(T x) T hadd(T x, T y) T madhi(T a, T b, T c) T madsat(T a, T b, T c) T max(T x, T y) T min(T x, T y) T mulhi(T x, T y) T popcount(T x) T rhadd(T x, T y) T rotate(T v, T i) T subsat(T x, T y) Relational Functions bool all(Tb x) bool any(Tb x) Tb isfinite(T x) Tb isinf(T x) Tb isnan(T x) Tb isnormal(T x) Tb isordered(T x, T y) Tb isunordered(T x, T y) Tb not(Tb x) T select(T a, T b, Tb c) Ti select(Ti a, Ti b, Tb c) Tb signbit(T x) Math Functions T acos(T x) T acosh(T x) T asin(T x)

Math Functions contd… T atanh(T x) T ceil(T x) T copysign(T x, T y) T cos(T x) T cosh(T x) T exp(T x) T exp2(T x) T exp10(T x) T fabs(T x) T abs(T x) T fdim(T x, T y) T floor(T x) T fmax(T x, T y) T max(T x, T y) T fmin(T x, T y) T min(T x, T y) T fmod(T x, T y) T fract(T x) T frexp(T x, Ti& exponent) Ti ilogb(T x) T ldexp(T x, Ti k) T log(T x) T log2(T x) T log10(T x) T modf(T x, T& intval) T pow(T x, T y) T powr(T x, T y) T rint(T x) T round(T x) T rsqrt(T x) T sin(T x) T sincos(T x, T& cosval) T sinh(T x) T sqrt(T x) T tan(T x) T tanh(T x) T trunc(T x) Geometric Functions T cross(T x, T y) Ts distance(T x, T y)

Geometric Functions contd… Ts length(T x) Ts length_squared(T x) T normalize(T x) T reflect(T I, T N) T refract(T I, T N, Ts eta) Compute Functions void work_group_barrier(mem_flags) Fragment Functions - Derivatives T dfdx(T p) T dfdy(T p) T fwidth(T p) Fragment Functions - Samples uint get_num_samples() float2 get_sample_position(uint indx) Fragment Functions - Flow Control void discard_fragment(void) Unpack Functions float4 unpack_unorm4x8_to_float(uint x) float4 unpack_snorm4x8_to_float(uint x) half4 unpack_unorm4x8_to_half(uint x) half4 unpack_snorm4x8_to_half(uint x) float4 unpack_unorm4x8_srgb_to_float(uint x) half4 unpack_unorm4x8_srgb_to_half(uint x) float2 unpack_unorm2x16_to_float(uint x) float2 unpack_snorm2x16_to_float(uint x) half2 unapck_unorm2x16_to_half(uint x) half2 unpack_snorm2x16_to_half(uint x) float4 unpack_unorm10a2_to_float(uint x) float3 unpack_unorm565_to_float(ushort x) half4 unpack_unorm10a2_to_half(uint x) half3 unpck_unorm565_to_half(ushort x) Pack Functions uint pack_float_to_unorm4x8(float4 x) uint pack_float_to_snorm4x8(float4 x) uint pack_half_to_unorm4x8(half4 x) uint pack_half_tosnorm4x8(half4 x) uint pack_float_to_srgb_unorm4x8(float4 x) uint pack_half_to_srgb_unorm4x8(half4 x) uint pack_float_to_unorm2x16(float2 x) uint pack_float_to_snorm2x16(float2 x)

Pack Functions contd… ushort pack_float_to_unorm565(float3 x) uint pack_half_to_unorm10a2(half4 x) ushort pack_half_to_unorm565(half3 x) Atomic Functions void atomic_store_explicit(…) void atomic_load_explicit(…) void atomic_exchange_explicit(…) void atomic_compare_exchange_weak_explicit(…) void atomic_fetch_key_explicit(…) Texture Functions Tv sample(sampler s, floatn coord, intn offset=0) Tv sample(sampler s, floatn coord, uint array, intn offset=0) Tv sample(sampler s, floatn coord, lod_options options, intn offset=0) Tv sample(sampler s, floatn coord, uint array, lod_options options, intn offset=0) Tv read(uintn coord, uint lod=0) Tv read(uintn coord, uint array, uint lod=0) void write(Tv color, uintn coord, uint lod=0) void write(Tv color, uintn coord, uint array, uint lod=0) Tv gather(sampler s, floatn coord, int2 offset=0, component c=component::x) Tv gather(sampler s, float2 coord, uint array, int2 offset=0, component c=component::x) T sample_compare(sampler s, float2 coord, float compare-val, int2 offset=0) T sample_compare(sampler s, float2 coord, float compare-val, lod_options options, int2 offset=0) T sample_compare(sampler s, float2 coord, uint array, float compare-val, int2 offset=0) T sample_compare(sampler s, float2 coord, uint array, float compare-val, lod_options options, int2 offset=0) Tv gather_compare(sampler s, float2 coord, float compare_val, int2 offset=0) Tv gather_compare(sampler s, float2 coord, uint array, float compare_val, int2 offset=0) uint get_width(uint lod=0) uint get_height(uint lod=0) uint get_depth(uint lod=0)

Page 236: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Metal Fundamentals

Building a Metal application • Initialization

• Drawing

• Uniforms and synchronization

Metal shading language • Writing shaders in Metal

• Data types in Metal

• Shader inputs, outputs, and matching rules

Page 237: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Metal Fundamentals

Building a Metal application • Initialization

• Drawing

• Uniforms and synchronization

Metal shading language • Writing shaders in Metal

• Data types in Metal

• Shader inputs, outputs, and matching rules

Call to action • Amaze us with how you use Metal

• Let us know how we can improve Metal

Page 238: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

More Information

Filip Iliescu Graphics and Games Technologies Evangelist [email protected]

Allan Schaffer Graphics and Games Technologies Evangelist [email protected]

Documentation http://developer.apple.com

Apple Developer Forums http://devforums.apple.com

Page 239: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Related Sessions

• What’s New in the Accelerate Framework Nob Hill Tuesday 10:15AM

• Working with Metal—Overview Pacific Heights Wednesday 9:00AM

• Working with Metal—Advanced Pacific Heights Wednesday 11:30AM

• Media Location Sunday 0:00PM

• Graphics and Games Location Sunday 0:00PM

• Core OS Location Sunday 0:00PM

• Special Events Location Sunday 0:00PM

Page 240: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer

Labs

• Metal Lab Graphics and Games Lab A Wednesday 2:00PM

• Metal Lab Graphics and Games Lab B Thursday 10:15AM

Page 241: Working with Metal—Fundamentals · Working with Metal—Fundamentals Session 604 Richard Schreyer GPU Software Engineer Graphics and Games! Aaftab Munshi GPU Software Engineer