1 // Copyright 2023 Google LLC
2 //
3 // Licensed under the Apache License, Version 2.0 (the "License");
4 // you may not use this file except in compliance with the License.
5 // You may obtain a copy of the License at
6 //
7 // http://www.apache.org/licenses/LICENSE-2.0
8 //
9 // Unless required by applicable law or agreed to in writing, software
10 // distributed under the License is distributed on an "AS IS" BASIS,
11 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 // See the License for the specific language governing permissions and
13 // limitations under the License.
14
15 #include "cpu_features_macros.h"
16
17 #ifdef CPU_FEATURES_ARCH_LOONGARCH
18 #if defined(CPU_FEATURES_OS_LINUX)
19
20 #include "cpuinfo_loongarch.h"
21
22 ////////////////////////////////////////////////////////////////////////////////
23 // Definitions for introspection.
24 ////////////////////////////////////////////////////////////////////////////////
25 #define INTROSPECTION_TABLE \
26 LINE(LOONGARCH_CPUCFG, CPUCFG, "cfg", HWCAP_LOONGARCH_CPUCFG, 0) \
27 LINE(LOONGARCH_LAM, LAM, "lam", HWCAP_LOONGARCH_LAM, 0) \
28 LINE(LOONGARCH_UAL, UAL, "ual", HWCAP_LOONGARCH_UAL, 0) \
29 LINE(LOONGARCH_FPU, FPU, "fpu", HWCAP_LOONGARCH_FPU, 0) \
30 LINE(LOONGARCH_LSX, LSX, "lsx", HWCAP_LOONGARCH_LSX, 0) \
31 LINE(LOONGARCH_LASX, LASX, "lasx", HWCAP_LOONGARCH_LASX, 0) \
32 LINE(LOONGARCH_CRC32, CRC32, "crc32", HWCAP_LOONGARCH_CRC32, 0) \
33 LINE(LOONGARCH_COMPLEX, COMPLEX, "complex", HWCAP_LOONGARCH_COMPLEX, 0) \
34 LINE(LOONGARCH_CRYPTO, CRYPTO, "crypto", HWCAP_LOONGARCH_CRYPTO, 0) \
35 LINE(LOONGARCH_LVZ, LVZ, "lvz", HWCAP_LOONGARCH_LVZ, 0) \
36 LINE(LOONGARCH_LBT_X86, LBT_X86, "lbt_x86", HWCAP_LOONGARCH_LBT_X86, 0) \
37 LINE(LOONGARCH_LBT_ARM, LBT_ARM, "lbt_arm", HWCAP_LOONGARCH_LBT_ARM, 0) \
38 LINE(LOONGARCH_LBT_MIPS, LBT_MIPS, "lbt_mips", HWCAP_LOONGARCH_LBT_MIPS, 0) \
39 LINE(LOONGARCH_PTW, PTW, "ptw", HWCAP_LOONGARCH_PTW, 0)
40 #define INTROSPECTION_PREFIX LoongArch
41 #define INTROSPECTION_ENUM_PREFIX LOONGARCH
42 #include "define_introspection_and_hwcaps.inl"
43
44 ////////////////////////////////////////////////////////////////////////////////
45 // Implementation.
46 ////////////////////////////////////////////////////////////////////////////////
47
48 #include <stdbool.h>
49 #include <stdio.h>
50
51 #include "internal/filesystem.h"
52 #include "internal/stack_line_reader.h"
53
54 static const LoongArchInfo kEmptyLoongArchInfo;
55
HandleLoongArchLine(const LineResult result,LoongArchInfo * const info)56 static bool HandleLoongArchLine(const LineResult result, LoongArchInfo* const info) {
57 StringView line = result.line;
58 StringView key, value;
59 if (CpuFeatures_StringView_GetAttributeKeyValue(line, &key, &value)) {
60 if (CpuFeatures_StringView_IsEquals(key, str("Features"))) {
61 for (size_t i = 0; i < LOONGARCH_LAST_; ++i) {
62 kSetters[i](&info->features, CpuFeatures_StringView_HasWord(
63 value, kCpuInfoFlags[i], ' '));
64 }
65 }
66 }
67 return !result.eof;
68 }
69
FillProcCpuInfoData(LoongArchInfo * const info)70 static void FillProcCpuInfoData(LoongArchInfo* const info) {
71 const int fd = CpuFeatures_OpenFile("/proc/cpuinfo");
72 if (fd >= 0) {
73 StackLineReader reader;
74 StackLineReader_Initialize(&reader, fd);
75 for (;;) {
76 if (!HandleLoongArchLine(StackLineReader_NextLine(&reader), info)) break;
77 }
78 CpuFeatures_CloseFile(fd);
79 }
80 }
81
GetLoongArchInfo(void)82 LoongArchInfo GetLoongArchInfo(void) {
83 LoongArchInfo info = kEmptyLoongArchInfo;
84 FillProcCpuInfoData(&info);
85 return info;
86 }
87
88 #endif // defined(CPU_FEATURES_OS_LINUX)
89 #endif // CPU_FEATURES_ARCH_LOONGARCH
90