decode.glsl (3421B)
1 /* See LICENSE for license details. */ 2 3 /* NOTE(rnp): invoked with samples x channels x transmits 4 * Each instance extracts a single time sample from a single channel for all transmits 5 * and does a dot product with the appropriate row of the bound hadamard matrix 6 * (unless decode_mode == DECODE_MODE_NONE). The result of this dot product is stored in the 7 * output. In bulk this has the effect of computing a matrix multiply of the 8 * sample-transmit plane with the bound hadamard matrix. 9 */ 10 11 #if DataKind == DataKind_Float32 12 #define INPUT_DATA_TYPE float 13 #define SAMPLE_DATA_TYPE float 14 #define SAMPLE_TYPE_CAST(x) (x) 15 #elif DataKind == DataKind_Float32Complex 16 #define INPUT_DATA_TYPE vec2 17 #define SAMPLE_DATA_TYPE vec2 18 #define SAMPLE_TYPE_CAST(x) (x) 19 #elif DataKind == DataKind_Int16Complex 20 #define INPUT_DATA_TYPE int 21 #define SAMPLE_DATA_TYPE vec2 22 #define SAMPLE_TYPE_CAST(x) vec2(((x) << 16) >> 16, (x) >> 16) 23 #elif DataKind == DataKind_Int16 24 #define INPUT_DATA_TYPE int 25 #define RF_SAMPLES_PER_INDEX 2 26 #if DilateOutput 27 #define SAMPLE_DATA_TYPE vec4 28 #define SAMPLE_TYPE_CAST(x) vec4(((x) << 16) >> 16, 0, (x) >> 16, 0) 29 #else 30 #define SAMPLE_DATA_TYPE vec2 31 #define SAMPLE_TYPE_CAST(x) vec2(((x) << 16) >> 16, (x) >> 16) 32 #define OUTPUT_SAMPLES_PER_INDEX 2 33 #endif 34 #else 35 #error unsupported data kind for Decode 36 #endif 37 38 #ifndef OUTPUT_SAMPLES_PER_INDEX 39 #define OUTPUT_SAMPLES_PER_INDEX 1 40 #endif 41 42 #ifndef RF_SAMPLES_PER_INDEX 43 #define RF_SAMPLES_PER_INDEX 1 44 #endif 45 46 layout(std430, binding = 1) readonly restrict buffer buffer_1 { 47 INPUT_DATA_TYPE rf_data[]; 48 }; 49 50 layout(std430, binding = 2) writeonly restrict buffer buffer_2 { 51 INPUT_DATA_TYPE out_rf_data[]; 52 }; 53 54 layout(std430, binding = 3) writeonly restrict buffer buffer_3 { 55 SAMPLE_DATA_TYPE out_data[]; 56 }; 57 58 layout(r32f, binding = 0) readonly restrict uniform image2D hadamard; 59 layout(r16i, binding = 1) readonly restrict uniform iimage1D channel_mapping; 60 61 SAMPLE_DATA_TYPE sample_rf_data(uint index) 62 { 63 SAMPLE_DATA_TYPE result = SAMPLE_TYPE_CAST(rf_data[index]); 64 return result; 65 } 66 67 void main() 68 { 69 uint time_sample = gl_GlobalInvocationID.x * RF_SAMPLES_PER_INDEX; 70 uint channel = gl_GlobalInvocationID.y; 71 uint transmit = gl_GlobalInvocationID.z; 72 73 uint rf_offset = (InputChannelStride * channel + TransmitCount * time_sample) / RF_SAMPLES_PER_INDEX; 74 if (u_first_pass) { 75 if (time_sample < InputTransmitStride) { 76 uint in_off = InputChannelStride * imageLoad(channel_mapping, int(channel)).x + 77 InputTransmitStride * transmit + 78 InputSampleStride * time_sample; 79 out_rf_data[rf_offset + transmit] = rf_data[in_off / RF_SAMPLES_PER_INDEX]; 80 } 81 } else { 82 if (time_sample < OutputTransmitStride) { 83 uint out_off = OutputChannelStride * channel + 84 OutputTransmitStride * transmit + 85 OutputSampleStride * time_sample; 86 87 SAMPLE_DATA_TYPE result = SAMPLE_DATA_TYPE(0); 88 switch (DecodeMode) { 89 case DecodeMode_None:{ 90 result = sample_rf_data(rf_offset + transmit); 91 }break; 92 case DecodeMode_Hadamard:{ 93 SAMPLE_DATA_TYPE sum = SAMPLE_DATA_TYPE(0); 94 for (int i = 0; i < TransmitCount; i++) 95 sum += imageLoad(hadamard, ivec2(i, transmit)).x * sample_rf_data(rf_offset++); 96 result = sum / float(TransmitCount); 97 }break; 98 } 99 out_data[out_off / OUTPUT_SAMPLES_PER_INDEX] = result; 100 } 101 } 102 }