Skip to content

Commit 410afda

Browse files
committed
added cpu detection and target ARMV6, used in raspberry pi
1 parent bf04544 commit 410afda

File tree

5 files changed

+477
-7
lines changed

5 files changed

+477
-7
lines changed

Makefile.arm

+7-2
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,12 @@
11

22
ifeq ($(CORE), ARMV7)
3-
CCOMMON_OPT += -marm -mfpu=vfpv3 -mfloat-abi=hard
4-
FCOMMON_OPT += -marm -mfpu=vfpv3 -mfloat-abi=hard
3+
CCOMMON_OPT += -marm -mfpu=vfpv3 -mfloat-abi=hard -march=armv7-a
4+
FCOMMON_OPT += -marm -mfpu=vfpv3 -mfloat-abi=hard -march=armv7-a
5+
endif
6+
7+
ifeq ($(CORE), ARMV6)
8+
CCOMMON_OPT += -marm -mfpu=vfp -mfloat-abi=hard -march=armv6
9+
FCOMMON_OPT += -marm -mfpu=vfp -mfloat-abi=hard -march=armv6
510
endif
611

712

cpuid_arm.c

+262
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,262 @@
1+
/**************************************************************************
2+
Copyright (c) 2013, The OpenBLAS Project
3+
All rights reserved.
4+
Redistribution and use in source and binary forms, with or without
5+
modification, are permitted provided that the following conditions are
6+
met:
7+
1. Redistributions of source code must retain the above copyright
8+
notice, this list of conditions and the following disclaimer.
9+
2. Redistributions in binary form must reproduce the above copyright
10+
notice, this list of conditions and the following disclaimer in
11+
the documentation and/or other materials provided with the
12+
distribution.
13+
3. Neither the name of the OpenBLAS project nor the names of
14+
its contributors may be used to endorse or promote products
15+
derived from this software without specific prior written permission.
16+
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
17+
AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
18+
IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
19+
ARE DISCLAIMED. IN NO EVENT SHALL THE OPENBLAS PROJECT OR CONTRIBUTORS BE
20+
LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
21+
DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
22+
SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
23+
CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
24+
OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE
25+
USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
26+
*****************************************************************************/
27+
28+
#include <string.h>
29+
30+
#define CPU_UNKNOWN 0
31+
#define CPU_ARMV6 1
32+
#define CPU_ARMV7 2
33+
#define CPU_CORTEXA15 3
34+
35+
static char *cpuname[] = {
36+
"UNKOWN",
37+
"ARMV6",
38+
"ARMV7",
39+
"CORTEXA15"
40+
};
41+
42+
43+
int get_feature(char *search)
44+
{
45+
46+
#ifdef linux
47+
FILE *infile;
48+
char buffer[2048], *p,*t;
49+
p = (char *) NULL ;
50+
51+
infile = fopen("/proc/cpuinfo", "r");
52+
53+
while (fgets(buffer, sizeof(buffer), infile))
54+
{
55+
56+
if (!strncmp("Features", buffer, 8))
57+
{
58+
p = strchr(buffer, ':') + 2;
59+
break;
60+
}
61+
}
62+
63+
fclose(infile);
64+
65+
66+
if( p == NULL ) return;
67+
68+
t = strtok(p," ");
69+
while( t = strtok(NULL," "))
70+
{
71+
if (!strcmp(t, search)) { return(1); }
72+
}
73+
74+
#endif
75+
return(0);
76+
}
77+
78+
79+
int detect(void)
80+
{
81+
82+
#ifdef linux
83+
84+
FILE *infile;
85+
char buffer[512], *p;
86+
p = (char *) NULL ;
87+
88+
infile = fopen("/proc/cpuinfo", "r");
89+
90+
while (fgets(buffer, sizeof(buffer), infile))
91+
{
92+
93+
if (!strncmp("model name", buffer, 10))
94+
{
95+
p = strchr(buffer, ':') + 2;
96+
break;
97+
}
98+
}
99+
100+
fclose(infile);
101+
102+
if(p != NULL)
103+
{
104+
105+
if (strstr(p, "ARMv7"))
106+
{
107+
if ( get_feature("vfpv4"))
108+
return CPU_ARMV7;
109+
110+
if ( get_feature("vfpv3"))
111+
return CPU_ARMV7;
112+
113+
if ( get_feature("vfp"))
114+
return CPU_ARMV6;
115+
116+
117+
}
118+
119+
if (strstr(p, "ARMv6"))
120+
{
121+
if ( get_feature("vfp"))
122+
return CPU_ARMV6;
123+
}
124+
125+
126+
}
127+
#endif
128+
129+
return CPU_UNKNOWN;
130+
}
131+
132+
char *get_corename(void)
133+
{
134+
return cpuname[detect()];
135+
}
136+
137+
void get_architecture(void)
138+
{
139+
printf("ARM");
140+
}
141+
142+
void get_subarchitecture(void)
143+
{
144+
int d = detect();
145+
switch (d)
146+
{
147+
148+
case CPU_ARMV7:
149+
printf("ARMV7");
150+
break;
151+
152+
case CPU_ARMV6:
153+
printf("ARMV6");
154+
break;
155+
156+
default:
157+
printf("UNKNOWN");
158+
break;
159+
}
160+
}
161+
162+
void get_subdirname(void)
163+
{
164+
printf("arm");
165+
}
166+
167+
void get_cpuconfig(void)
168+
{
169+
170+
int d = detect();
171+
switch (d)
172+
{
173+
174+
case CPU_ARMV7:
175+
printf("#define ARMV7\n");
176+
printf("#define HAVE_VFP\n");
177+
printf("#define HAVE_VFPV3\n");
178+
if ( get_feature("neon")) printf("#define HAVE_NEON\n");
179+
if ( get_feature("vfpv4")) printf("#define HAVE_VFPV4\n");
180+
printf("#define L1_DATA_SIZE 65536\n");
181+
printf("#define L1_DATA_LINESIZE 32\n");
182+
printf("#define L2_SIZE 512488\n");
183+
printf("#define L2_LINESIZE 32\n");
184+
printf("#define DTB_DEFAULT_ENTRIES 64\n");
185+
printf("#define DTB_SIZE 4096\n");
186+
printf("#define L2_ASSOCIATIVE 4\n");
187+
break;
188+
189+
case CPU_ARMV6:
190+
printf("#define ARMV6\n");
191+
printf("#define HAVE_VFP\n");
192+
printf("#define L1_DATA_SIZE 65536\n");
193+
printf("#define L1_DATA_LINESIZE 32\n");
194+
printf("#define L2_SIZE 512488\n");
195+
printf("#define L2_LINESIZE 32\n");
196+
printf("#define DTB_DEFAULT_ENTRIES 64\n");
197+
printf("#define DTB_SIZE 4096\n");
198+
printf("#define L2_ASSOCIATIVE 4\n");
199+
break;
200+
201+
}
202+
}
203+
204+
205+
void get_libname(void)
206+
{
207+
208+
int d = detect();
209+
switch (d)
210+
{
211+
212+
case CPU_ARMV7:
213+
printf("armv7\n");
214+
break;
215+
216+
case CPU_ARMV6:
217+
printf("armv6\n");
218+
break;
219+
220+
}
221+
}
222+
223+
224+
void get_features(void)
225+
{
226+
227+
#ifdef linux
228+
FILE *infile;
229+
char buffer[2048], *p,*t;
230+
p = (char *) NULL ;
231+
232+
infile = fopen("/proc/cpuinfo", "r");
233+
234+
while (fgets(buffer, sizeof(buffer), infile))
235+
{
236+
237+
if (!strncmp("Features", buffer, 8))
238+
{
239+
p = strchr(buffer, ':') + 2;
240+
break;
241+
}
242+
}
243+
244+
fclose(infile);
245+
246+
247+
if( p == NULL ) return;
248+
249+
t = strtok(p," ");
250+
while( t = strtok(NULL," "))
251+
{
252+
if (!strcmp(t, "vfp")) { printf("HAVE_VFP=1\n"); continue; }
253+
if (!strcmp(t, "vfpv3")) { printf("HAVE_VFPV3=1\n"); continue; }
254+
if (!strcmp(t, "vfpv4")) { printf("HAVE_VFPV4=1\n"); continue; }
255+
if (!strcmp(t, "neon")) { printf("HAVE_NEON=1\n"); continue; }
256+
}
257+
258+
#endif
259+
return;
260+
}
261+
262+

getarch.c

+34-5
Original file line numberDiff line numberDiff line change
@@ -687,23 +687,42 @@ USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
687687
#define ARCHCONFIG "-DARMV7 " \
688688
"-DL1_DATA_SIZE=65536 -DL1_DATA_LINESIZE=32 " \
689689
"-DL2_SIZE=512488 -DL2_LINESIZE=32 " \
690-
"-DDTB_DEFAULT_ENTRIES=64 -DDTB_SIZE=4096 -DL2_ASSOCIATIVE=4 "
690+
"-DDTB_DEFAULT_ENTRIES=64 -DDTB_SIZE=4096 -DL2_ASSOCIATIVE=4 " \
691+
"-DHAVE_VFPV3 -DHAVE_VFP"
691692
#define LIBNAME "armv7"
692693
#define CORENAME "ARMV7"
693694
#else
694695
#endif
695696

697+
#ifdef FORCE_ARMV6
698+
#define FORCE
699+
#define ARCHITECTURE "ARM"
700+
#define SUBARCHITECTURE "ARMV6"
701+
#define SUBDIRNAME "arm"
702+
#define ARCHCONFIG "-DARMV6 " \
703+
"-DL1_DATA_SIZE=65536 -DL1_DATA_LINESIZE=32 " \
704+
"-DL2_SIZE=512488 -DL2_LINESIZE=32 " \
705+
"-DDTB_DEFAULT_ENTRIES=64 -DDTB_SIZE=4096 -DL2_ASSOCIATIVE=4 " \
706+
"-DHAVE_VFP"
707+
#define LIBNAME "armv6"
708+
#define CORENAME "ARMV6"
709+
#else
710+
#endif
711+
712+
696713

697714
#ifndef FORCE
698715

699716
#if defined(__powerpc__) || defined(__powerpc) || defined(powerpc) || \
700-
defined(__PPC__) || defined(PPC) || defined(_POWER) || defined(__POWERPC__)
717+
defined(__PPC__) || defined(PPC) || defined(_POWER) || defined(__POWERPC__)
718+
701719
#ifndef POWER
702720
#define POWER
703721
#endif
704722
#define OPENBLAS_SUPPORTED
705723
#endif
706724

725+
707726
#if defined(__i386__) || (__x86_64__)
708727
#include "cpuid_x86.c"
709728
#define OPENBLAS_SUPPORTED
@@ -734,12 +753,16 @@ USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
734753
#define OPENBLAS_SUPPORTED
735754
#endif
736755

756+
#ifdef __arm__
757+
#include "cpuid_arm.c"
758+
#define OPENBLAS_SUPPORTED
759+
#endif
760+
761+
737762
#ifndef OPENBLAS_SUPPORTED
738763
#error "This arch/CPU is not supported by OpenBLAS."
739764
#endif
740765

741-
#else
742-
743766
#endif
744767

745768
static int get_num_cores(void) {
@@ -788,7 +811,7 @@ int main(int argc, char *argv[]){
788811
#ifdef FORCE
789812
printf("CORE=%s\n", CORENAME);
790813
#else
791-
#if defined(__i386__) || defined(__x86_64__) || defined(POWER) || defined(__mips__)
814+
#if defined(__i386__) || defined(__x86_64__) || defined(POWER) || defined(__mips__) || defined(__arm__)
792815
printf("CORE=%s\n", get_corename());
793816
#endif
794817
#endif
@@ -803,6 +826,12 @@ int main(int argc, char *argv[]){
803826

804827
printf("NUM_CORES=%d\n", get_num_cores());
805828

829+
#if defined(__arm__) && !defined(FORCE)
830+
get_features();
831+
#endif
832+
833+
834+
806835
#if defined(__i386__) || defined(__x86_64__)
807836
#ifndef FORCE
808837
get_sse();

0 commit comments

Comments
 (0)