xref: /aosp_15_r20/external/OpenCL-ICD-Loader/loader/cllayerinfo.c (revision 1cddb830dba8aa7c1cc1039338e56b3b9fa24952)
1 /*
2  * Copyright (c) 2022 The Khronos Group Inc.
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *     http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  *
16  * OpenCL is a trademark of Apple Inc. used under license by Khronos.
17  */
18 
19 #include "icd.h"
20 #include <stdio.h>
21 #include <stdlib.h>
22 #include <CL/cl_layer.h>
23 #if defined(_WIN32)
24 #include <io.h>
25 #include <share.h>
26 #include <sys/stat.h>
27 #else
28 #include <unistd.h>
29 #endif
30 #include <fcntl.h>
31 
32 int stdout_bak, stderr_bak;
33 
34 // Temporarily deactivate stdout:
35 // https://stackoverflow.com/a/4832902
36 
37 #if defined(_WIN32)
38 #define SECURE 1
39 #define OPEN _open
40 #define OPEN_FLAGS _O_WRONLY
41 #define CLOSE _close
42 #define DUP _dup
43 #define DUP2 _dup2
44 #define NULL_STREAM "nul"
45 #else
46 #define OPEN open
47 #define OPEN_FLAGS O_WRONLY
48 #define CLOSE close
49 #define DUP dup
50 #define DUP2 dup2
51 #define NULL_STREAM "/dev/null"
52 #endif
53 
54 static inline int
silence_stream(FILE * file,int fd)55 silence_stream(FILE *file, int fd)
56 {
57     int new_fd, fd_bak;
58     fflush(file);
59     fd_bak = DUP(fd);
60 #if defined(_WIN32) && SECURE
61     _sopen_s(&new_fd, NULL_STREAM, OPEN_FLAGS, _SH_DENYNO, _S_IWRITE);
62 #else
63     new_fd = OPEN(NULL_STREAM, OPEN_FLAGS);
64 #endif
65     DUP2(new_fd, fd);
66     CLOSE(new_fd);
67     return fd_bak;
68 }
69 
silence_layers(void)70 static void silence_layers(void)
71 {
72     stdout_bak = silence_stream(stdout, 1);
73     stderr_bak = silence_stream(stderr, 2);
74 }
75 
76 static inline void
restore_stream(FILE * file,int fd,int fd_bak)77 restore_stream(FILE *file, int fd, int fd_bak)
78 {
79     fflush(file);
80     DUP2(fd_bak, fd);
81     CLOSE(fd_bak);
82 }
83 
restore_outputs(void)84 static void restore_outputs(void)
85 {
86     restore_stream(stdout, 1, stdout_bak);
87     restore_stream(stderr, 2, stderr_bak);
88 }
89 
printLayerInfo(const struct KHRLayer * layer)90 void printLayerInfo(const struct KHRLayer *layer)
91 {
92     cl_layer_api_version api_version = 0;
93     pfn_clGetLayerInfo p_clGetLayerInfo = (pfn_clGetLayerInfo)(size_t)layer->p_clGetLayerInfo;
94     cl_int result = CL_SUCCESS;
95     size_t sz;
96 
97     printf("%s:\n", layer->libraryName);
98     result = p_clGetLayerInfo(CL_LAYER_API_VERSION, sizeof(api_version), &api_version, NULL);
99     if (CL_SUCCESS == result)
100         printf("\tCL_LAYER_API_VERSION: %d\n", (int)api_version);
101 
102     result = p_clGetLayerInfo(CL_LAYER_NAME, 0, NULL, &sz);
103     if (CL_SUCCESS == result)
104     {
105         char *name = (char *)malloc(sz);
106         if (name)
107         {
108             result = p_clGetLayerInfo(CL_LAYER_NAME, sz, name, NULL);
109             if (CL_SUCCESS == result)
110                  printf("\tCL_LAYER_NAME: %s\n", name);
111             free(name);
112         }
113     }
114 }
115 
main(int argc,char * argv[])116 int main (int argc, char *argv[])
117 {
118     (void)argc;
119     (void)argv;
120     silence_layers();
121     atexit(restore_outputs);
122     khrIcdInitialize();
123     restore_outputs();
124     atexit(silence_layers);
125     const struct KHRLayer *layer = khrFirstLayer;
126     while (layer)
127     {
128         printLayerInfo(layer);
129         layer = layer->next;
130     }
131     return 0;
132 }
133