From: Shivraj Patil <shivraj.pa...@imgtec.com> Signed-off-by: Shivraj Patil <shivraj.pa...@imgtec.com> --- libavcodec/mips/hevcdsp_init_mips.c | 6 +- libavutil/cpu.c | 35 ++++++++++ libavutil/cpu.h | 8 +++ libavutil/cpu_internal.h | 1 + libavutil/mips/Makefile | 1 + libavutil/mips/cpu.c | 124 +++++++++++++++++++++++++++++++++++ libavutil/mips/cpu.h | 36 ++++++++++ 7 files changed, 210 insertions(+), 1 deletion(-) create mode 100644 libavutil/mips/cpu.c create mode 100644 libavutil/mips/cpu.h
diff --git a/libavcodec/mips/hevcdsp_init_mips.c b/libavcodec/mips/hevcdsp_init_mips.c index 3675b93..499d2e8 100644 --- a/libavcodec/mips/hevcdsp_init_mips.c +++ b/libavcodec/mips/hevcdsp_init_mips.c @@ -19,6 +19,7 @@ */ #include "libavcodec/mips/hevcdsp_mips.h" +#include "libavutil/mips/cpu.h" #if HAVE_MSA static av_cold void hevc_dsp_init_msa(HEVCDSPContext *c, @@ -449,6 +450,9 @@ static av_cold void hevc_dsp_init_msa(HEVCDSPContext *c, void ff_hevc_dsp_init_mips(HEVCDSPContext *c, const int bit_depth) { #if HAVE_MSA - hevc_dsp_init_msa(c, bit_depth); + int cpu_flags = av_get_cpu_flags(); + + if (have_msa(cpu_flags)) + hevc_dsp_init_msa(c, bit_depth); #endif // #if HAVE_MSA } diff --git a/libavutil/cpu.c b/libavutil/cpu.c index 780368d..1e716c6 100644 --- a/libavutil/cpu.c +++ b/libavutil/cpu.c @@ -86,6 +86,8 @@ int av_get_cpu_flags(void) flags = ff_get_cpu_flags_ppc(); if (ARCH_X86) flags = ff_get_cpu_flags_x86(); + if (ARCH_MIPS) + flags = ff_get_cpu_flags_mips(); checked = 1; return flags; @@ -156,6 +158,17 @@ int av_parse_cpu_flags(const char *s) { "armv8", NULL, 0, AV_OPT_TYPE_CONST, { .i64 = AV_CPU_FLAG_ARMV8 }, .unit = "flags" }, { "neon", NULL, 0, AV_OPT_TYPE_CONST, { .i64 = AV_CPU_FLAG_NEON }, .unit = "flags" }, { "vfp", NULL, 0, AV_OPT_TYPE_CONST, { .i64 = AV_CPU_FLAG_VFP }, .unit = "flags" }, +#elif ARCH_MIPS + { "mipsfpu", NULL, 0, AV_OPT_TYPE_CONST, { .i64 = AV_CPU_FLAG_MIPSFPU }, .unit = "flags" }, + { "mips32r2", NULL, 0, AV_OPT_TYPE_CONST, { .i64 = AV_CPU_FLAG_MIPS32R2 }, .unit = "flags" }, + { "mips32r5", NULL, 0, AV_OPT_TYPE_CONST, { .i64 = AV_CPU_FLAG_MIPS32R5 }, .unit = "flags" }, + { "dspr1", NULL, 0, AV_OPT_TYPE_CONST, { .i64 = AV_CPU_FLAG_MIPSDSPR1 }, .unit = "flags" }, + { "dspr2", NULL, 0, AV_OPT_TYPE_CONST, { .i64 = AV_CPU_FLAG_MIPSDSPR2 }, .unit = "flags" }, + { "msa", NULL, 0, AV_OPT_TYPE_CONST, { .i64 = AV_CPU_FLAG_MSA }, .unit = "flags" }, +#elif ARCH_MIPS64 + { "mipsfpu", NULL, 0, AV_OPT_TYPE_CONST, { .i64 = AV_CPU_FLAG_MIPSFPU }, .unit = "flags" }, + { "mips64r6", NULL, 0, AV_OPT_TYPE_CONST, { .i64 = AV_CPU_FLAG_MIPS64R6 }, .unit = "flags" }, + { "msa", NULL, 0, AV_OPT_TYPE_CONST, { .i64 = AV_CPU_FLAG_MSA }, .unit = "flags" }, #endif { NULL }, }; @@ -234,6 +247,17 @@ int av_parse_cpu_caps(unsigned *flags, const char *s) { "armv8", NULL, 0, AV_OPT_TYPE_CONST, { .i64 = AV_CPU_FLAG_ARMV8 }, .unit = "flags" }, { "neon", NULL, 0, AV_OPT_TYPE_CONST, { .i64 = AV_CPU_FLAG_NEON }, .unit = "flags" }, { "vfp", NULL, 0, AV_OPT_TYPE_CONST, { .i64 = AV_CPU_FLAG_VFP }, .unit = "flags" }, +#elif ARCH_MIPS + { "mipsfpu", NULL, 0, AV_OPT_TYPE_CONST, { .i64 = AV_CPU_FLAG_MIPSFPU }, .unit = "flags" }, + { "mips32r2", NULL, 0, AV_OPT_TYPE_CONST, { .i64 = AV_CPU_FLAG_MIPS32R2 }, .unit = "flags" }, + { "mips32r5", NULL, 0, AV_OPT_TYPE_CONST, { .i64 = AV_CPU_FLAG_MIPS32R5 }, .unit = "flags" }, + { "dspr1", NULL, 0, AV_OPT_TYPE_CONST, { .i64 = AV_CPU_FLAG_MIPSDSPR1 }, .unit = "flags" }, + { "dspr2", NULL, 0, AV_OPT_TYPE_CONST, { .i64 = AV_CPU_FLAG_MIPSDSPR2 }, .unit = "flags" }, + { "msa", NULL, 0, AV_OPT_TYPE_CONST, { .i64 = AV_CPU_FLAG_MSA }, .unit = "flags" }, +#elif ARCH_MIPS64 + { "mipsfpu", NULL, 0, AV_OPT_TYPE_CONST, { .i64 = AV_CPU_FLAG_MIPSFPU }, .unit = "flags" }, + { "mips64r6", NULL, 0, AV_OPT_TYPE_CONST, { .i64 = AV_CPU_FLAG_MIPS64R6 }, .unit = "flags" }, + { "msa", NULL, 0, AV_OPT_TYPE_CONST, { .i64 = AV_CPU_FLAG_MSA }, .unit = "flags" }, #endif { NULL }, }; @@ -334,6 +358,17 @@ static const struct { { AV_CPU_FLAG_AVX2, "avx2" }, { AV_CPU_FLAG_BMI1, "bmi1" }, { AV_CPU_FLAG_BMI2, "bmi2" }, +#elif ARCH_MIPS + { AV_CPU_FLAG_MIPSFPU, "mipsfpu" }, + { AV_CPU_FLAG_MIPS32R2, "mips32r2" }, + { AV_CPU_FLAG_MIPS32R5, "mips32r5" }, + { AV_CPU_FLAG_MIPSDSPR1, "dspr1" }, + { AV_CPU_FLAG_MIPSDSPR2, "dspr2" }, + { AV_CPU_FLAG_MSA, "msa" }, +#elif ARCH_MIPS64 + { AV_CPU_FLAG_MIPSFPU "mipsfpu" }, + { AV_CPU_FLAG_MIPS64R6 "mips64r6" }, + { AV_CPU_FLAG_MSA "msa" }, #endif { 0 } }; diff --git a/libavutil/cpu.h b/libavutil/cpu.h index 9403eca..a636d99 100644 --- a/libavutil/cpu.h +++ b/libavutil/cpu.h @@ -65,6 +65,14 @@ #define AV_CPU_FLAG_ARMV8 (1 << 6) #define AV_CPU_FLAG_SETEND (1 <<16) +#define AV_CPU_FLAG_MIPSFPU (1 << 0) +#define AV_CPU_FLAG_MIPS32R2 (1 << 1) +#define AV_CPU_FLAG_MIPS32R5 (1 << 2) +#define AV_CPU_FLAG_MIPS64R6 (1 << 3) +#define AV_CPU_FLAG_MIPSDSPR1 (1 << 4) +#define AV_CPU_FLAG_MIPSDSPR2 (1 << 5) +#define AV_CPU_FLAG_MSA (1 << 6) + /** * Return the flags which specify extensions supported by the CPU. * The returned value is affected by av_force_cpu_flags() if that was used diff --git a/libavutil/cpu_internal.h b/libavutil/cpu_internal.h index 2105298..bedbcfb 100644 --- a/libavutil/cpu_internal.h +++ b/libavutil/cpu_internal.h @@ -40,5 +40,6 @@ int ff_get_cpu_flags_aarch64(void); int ff_get_cpu_flags_arm(void); int ff_get_cpu_flags_ppc(void); int ff_get_cpu_flags_x86(void); +int ff_get_cpu_flags_mips(void); #endif /* AVUTIL_CPU_INTERNAL_H */ diff --git a/libavutil/mips/Makefile b/libavutil/mips/Makefile index dbfa5aa..c83c6de 100644 --- a/libavutil/mips/Makefile +++ b/libavutil/mips/Makefile @@ -1 +1,2 @@ OBJS += mips/float_dsp_mips.o +OBJS += mips/cpu.o diff --git a/libavutil/mips/cpu.c b/libavutil/mips/cpu.c new file mode 100644 index 0000000..45ebfe1 --- /dev/null +++ b/libavutil/mips/cpu.c @@ -0,0 +1,124 @@ +/* + * Copyright (c) 2015 Manojkumar Bhosale (manojkumar.bhos...@imgtec.com) + * + * This file is part of FFmpeg. + * + * FFmpeg is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * FFmpeg is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with FFmpeg; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA + */ + +#include <stdint.h> +#include <stdio.h> +#include <string.h> + +#include "libavutil/cpu.h" +#include "libavutil/cpu_internal.h" +#include "libavutil/avstring.h" +#include "config.h" + +#define CORE_FLAG(f) \ + (AV_CPU_FLAG_ ## f * (HAVE_ ## f || HAVE_ ## f ## _EXTERNAL || HAVE_ ## f ## _INLINE)) + +#define CORE_CPU_FLAGS \ + (CORE_FLAG(MIPSFPU) | \ + CORE_FLAG(MIPS32R2) | \ + CORE_FLAG(MIPS32R5) | \ + CORE_FLAG(MIPS64R6) | \ + CORE_FLAG(MIPSDSPR1) | \ + CORE_FLAG(MIPSDSPR2) | \ + CORE_FLAG(MSA)) + +#define HWCAP_VZ (1 << 0) +#define HWCAP_EVA (1 << 1) +#define HWCAP_HTW (1 << 2) +#define HWCAP_FPU (1 << 3) +#define HWCAP_MIPS32R2 (1 << 4) +#define HWCAP_MIPS32R5 (1 << 5) +#define HWCAP_MIPS64R6 (1 << 6) +#define HWCAP_DSPR1 (1 << 7) +#define HWCAP_DSPR2 (1 << 8) +#define HWCAP_MSA (1 << 9) + +static int get_cpuinfo(uint32_t *hwcap) +{ + FILE *f = fopen("/proc/cpuinfo", "r"); + char buf[200]; + + if (!f) + return -1; + + *hwcap = 0; + while (fgets(buf, sizeof(buf), f)) { + if (av_strstart(buf, "isa", NULL)) { + if (strstr(buf, "mips32r2")) + *hwcap |= HWCAP_MIPS32R2; + if (strstr(buf, "mips32r5")) + *hwcap |= HWCAP_MIPS32R5; + if (strstr(buf, "mips64r6")) + *hwcap |= HWCAP_MIPS64R6; + } + + if (av_strstart(buf, "ASEs implemented", NULL)) { + if (strstr(buf, "vz")) + *hwcap |= HWCAP_VZ; + if (strstr(buf, "eva")) + *hwcap |= HWCAP_EVA; + if (strstr(buf, "htw")) + *hwcap |= HWCAP_HTW; + if (strstr(buf, "msa")) + { + *hwcap |= HWCAP_MSA; + *hwcap |= HWCAP_FPU; + } + if (strstr(buf, "dsp")) + *hwcap |= HWCAP_DSPR1; + if (strstr(buf, "dsp2")) + *hwcap |= HWCAP_DSPR2; + break; + } + } + + fclose(f); + return 0; +} + +int ff_get_cpu_flags_mips(void) +{ + int cpuflags = CORE_CPU_FLAGS; + int hwcpuflags = 0; + uint32_t hwcap; + +#if !CONFIG_RUNTIME_CPUDETECT + return cpuflags; +#endif + + if (get_cpuinfo(&hwcap) < 0) + return cpuflags; + +#define set_cpucap(cap, flag) do { \ + if ((hwcap & HWCAP_ ## cap) && (cpuflags & CORE_FLAG(flag))) \ + hwcpuflags |= AV_CPU_FLAG_ ## flag; \ + } while (0) + + /* add ISA and ASE capabilities in cpuflags */ + set_cpucap(FPU, MIPSFPU); + set_cpucap(MIPS32R2, MIPS32R2); + set_cpucap(MIPS32R5, MIPS32R5); + set_cpucap(MIPS64R6, MIPS64R6); + set_cpucap(DSPR1, MIPSDSPR1); + set_cpucap(DSPR2, MIPSDSPR2); + set_cpucap(MSA, MSA); + + return hwcpuflags; +} diff --git a/libavutil/mips/cpu.h b/libavutil/mips/cpu.h new file mode 100644 index 0000000..24813f6 --- /dev/null +++ b/libavutil/mips/cpu.h @@ -0,0 +1,36 @@ +/* + * Copyright (c) 2015 Manojkumar Bhosale (manojkumar.bhos...@imgtec.com) + * + * This file is part of FFmpeg. + * + * FFmpeg is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * FFmpeg is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with FFmpeg; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA + */ + +#ifndef AVUTIL_MIPS_CPU_H +#define AVUTIL_MIPS_CPU_H + +#include "config.h" +#include "libavutil/cpu.h" +#include "libavutil/cpu_internal.h" + +#define have_mipsfpu(flags) CPUEXT(flags, MIPSFPU) +#define have_mips32r2(flags) CPUEXT(flags, MIPS32R2) +#define have_mips32r5(flags) CPUEXT(flags, MIPS32R5) +#define have_mips64r6(flags) CPUEXT(flags, MIPS64R6) +#define have_mipsdspr1(flags) CPUEXT(flags, MIPSDSPR1) +#define have_mipsdspr2(flags) CPUEXT(flags, MIPSDSPR2) +#define have_msa(flags) CPUEXT(flags, MSA) + +#endif /* #ifndef AVUTIL_MIPS_CPU_H */ -- 1.7.9.5 _______________________________________________ ffmpeg-devel mailing list ffmpeg-devel@ffmpeg.org http://ffmpeg.org/mailman/listinfo/ffmpeg-devel