gid = ivec2(gl_GlobalInvocationID.xy); if (gid.x >= out_width || gid.y >= out_height) { return; } int linear_index = gid.y * out_width + gid.x; #ifdef TWO_CHANNEL_INPUT vec2 input_value = input_data.elements[linear_index]; #else vec2 input_value = vec2(input_data.elements[linear_index], 0.0); #endif // TWO_CHANNEL_INPUT // Run activation function. // One and only one of FN_SOFTMAX,FN_SIGMOID,FN_NONE will be defined. #ifdef FN_SOFTMAX // Only two channel input tensor is supported. vec2 input_px = input_value.rg; float shift = max(input_px.r, input_px.g); float softmax_denom = exp(input_px.r - shift) + exp(input_px.g - shift); float new_mask_value = exp(input_px[OUTPUT_LAYER_INDEX] - shift) / softmax_denom; #endif // FN_SOFTMAX #ifdef FN_SIGMOID float new_mask_value = 1.0 / (exp(-input_value.r) + 1.0); #endif // FN_SIGMOID #ifdef FN_NONE float new_mask_value = input_value.r; #endif // FN_NONE #ifdef FLIP_Y_COORD int y_coord = out_height - gid.y - 1; #else int y_coord = gid.y; #endif // defined(FLIP_Y_COORD) ivec2 output_coordinate = ivec2(gid.x, y_coord); vec4 out_value = vec4(new_mask_value, 0.0, 0.0, new_mask_value); imageStore(output_texture, output_coordinate, out_value); }