Add support for LoongArch

Message ID 20221203134707.2197078-1-hengqi.chen@gmail.com
State Committed
Headers
Series Add support for LoongArch |

Commit Message

Hengqi Chen Dec. 3, 2022, 1:47 p.m. UTC
  This implements initial support for the LoongArch architecture.

Signed-off-by: Hengqi Chen <hengqi.chen@gmail.com>
---
 backends/ChangeLog           |  7 ++++
 backends/Makefile.am         |  7 +++-
 backends/loongarch_init.c    | 50 ++++++++++++++++++++++
 backends/loongarch_reloc.def | 81 ++++++++++++++++++++++++++++++++++++
 backends/loongarch_symbol.c  | 74 ++++++++++++++++++++++++++++++++
 libebl/ChangeLog             |  4 ++
 libebl/eblopenbackend.c      |  2 +
 src/ChangeLog                |  4 ++
 src/elflint.c                |  2 +-
 9 files changed, 228 insertions(+), 3 deletions(-)
 create mode 100644 backends/loongarch_init.c
 create mode 100644 backends/loongarch_reloc.def
 create mode 100644 backends/loongarch_symbol.c
  

Comments

Hengqi Chen Dec. 12, 2022, 8:12 a.m. UTC | #1
Hi, Mark:

Any comments? Thanks.

With this patch, pahole is now able to convert dwarf to BTF on
LoongArch machine.


cheers,
--
Hengqi


On Sat, Dec 3, 2022 at 9:47 PM Hengqi Chen <hengqi.chen@gmail.com> wrote:
>
> This implements initial support for the LoongArch architecture.
>
> Signed-off-by: Hengqi Chen <hengqi.chen@gmail.com>
> ---
>  backends/ChangeLog           |  7 ++++
>  backends/Makefile.am         |  7 +++-
>  backends/loongarch_init.c    | 50 ++++++++++++++++++++++
>  backends/loongarch_reloc.def | 81 ++++++++++++++++++++++++++++++++++++
>  backends/loongarch_symbol.c  | 74 ++++++++++++++++++++++++++++++++
>  libebl/ChangeLog             |  4 ++
>  libebl/eblopenbackend.c      |  2 +
>  src/ChangeLog                |  4 ++
>  src/elflint.c                |  2 +-
>  9 files changed, 228 insertions(+), 3 deletions(-)
>  create mode 100644 backends/loongarch_init.c
>  create mode 100644 backends/loongarch_reloc.def
>  create mode 100644 backends/loongarch_symbol.c
>
> diff --git a/backends/ChangeLog b/backends/ChangeLog
> index 5b0daffe..5813ddcc 100644
> --- a/backends/ChangeLog
> +++ b/backends/ChangeLog
> @@ -1,3 +1,10 @@
> +2022-12-02  Hengqi Chen  <hengqi.chen@gmail.com>
> +
> +       * Makefile.am (modules): Add loongarch.
> +       * loongarch_init.c: New file.
> +       * loongarch_reloc.def: New file.
> +       * loongarch_symbol.c: New file.
> +
>  2022-08-09  Andreas Schwab  <schwab@suse.de>
>
>         * riscv_init.c (riscv_init): HOOK segment_type_name,
> diff --git a/backends/Makefile.am b/backends/Makefile.am
> index 9566377f..0824123d 100644
> --- a/backends/Makefile.am
> +++ b/backends/Makefile.am
> @@ -37,7 +37,7 @@ AM_CPPFLAGS += -I$(top_srcdir)/libebl -I$(top_srcdir)/libasm \
>  noinst_LIBRARIES = libebl_backends.a libebl_backends_pic.a
>
>  modules = i386 sh x86_64 ia64 alpha arm aarch64 sparc ppc ppc64 s390 \
> -         m68k bpf riscv csky
> +         m68k bpf riscv csky loongarch
>
>  i386_SRCS = i386_init.c i386_symbol.c i386_corenote.c i386_cfi.c \
>             i386_retval.c i386_regs.c i386_auxv.c \
> @@ -96,11 +96,14 @@ riscv_SRCS = riscv_init.c riscv_symbol.c riscv_cfi.c riscv_regs.c \
>  csky_SRCS = csky_attrs.c csky_init.c csky_symbol.c csky_cfi.c \
>             csky_regs.c csky_initreg.c csky_corenote.c
>
> +loongarch_SRCS = loongarch_init.c loongarch_symbol.c
> +
>  libebl_backends_a_SOURCES = $(i386_SRCS) $(sh_SRCS) $(x86_64_SRCS) \
>                             $(ia64_SRCS) $(alpha_SRCS) $(arm_SRCS) \
>                             $(aarch64_SRCS) $(sparc_SRCS) $(ppc_SRCS) \
>                             $(ppc64_SRCS) $(s390_SRCS) \
> -                           $(m68k_SRCS) $(bpf_SRCS) $(riscv_SRCS) $(csky_SRCS)
> +                           $(m68k_SRCS) $(bpf_SRCS) $(riscv_SRCS) $(csky_SRCS) \
> +                           $(loongarch_SRCS)
>
>  libebl_backends_pic_a_SOURCES =
>  am_libebl_backends_pic_a_OBJECTS = $(libebl_backends_a_SOURCES:.c=.os)
> diff --git a/backends/loongarch_init.c b/backends/loongarch_init.c
> new file mode 100644
> index 00000000..a8ed9e81
> --- /dev/null
> +++ b/backends/loongarch_init.c
> @@ -0,0 +1,50 @@
> +/* Initialization of LoongArch specific backend library.
> +   Copyright (C) 2022 Hengqi Chen
> +   This file is part of elfutils.
> +
> +   This file is free software; you can redistribute it and/or modify
> +   it under the terms of either
> +
> +     * the GNU Lesser General Public License as published by the Free
> +       Software Foundation; either version 3 of the License, or (at
> +       your option) any later version
> +
> +   or
> +
> +     * the GNU General Public License as published by the Free
> +       Software Foundation; either version 2 of the License, or (at
> +       your option) any later version
> +
> +   or both in parallel, as here.
> +
> +   elfutils 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
> +   General Public License for more details.
> +
> +   You should have received copies of the GNU General Public License and
> +   the GNU Lesser General Public License along with this program.  If
> +   not, see <http://www.gnu.org/licenses/>.  */
> +
> +#ifdef HAVE_CONFIG_H
> +# include <config.h>
> +#endif
> +
> +#define BACKEND                loongarch_
> +#define RELOC_PREFIX   R_LARCH_
> +#include "libebl_CPU.h"
> +
> +/* This defines the common reloc hooks based on loongarch_reloc.def.  */
> +#include "common-reloc.c"
> +
> +
> +Ebl *
> +loongarch_init (Elf *elf __attribute__ ((unused)),
> +               GElf_Half machine __attribute__ ((unused)),
> +               Ebl *eh)
> +{
> +  loongarch_init_reloc (eh);
> +  HOOK (eh, reloc_simple_type);
> +
> +  return eh;
> +}
> diff --git a/backends/loongarch_reloc.def b/backends/loongarch_reloc.def
> new file mode 100644
> index 00000000..dd4a6b6d
> --- /dev/null
> +++ b/backends/loongarch_reloc.def
> @@ -0,0 +1,81 @@
> +/* List the relocation types for LoongArch.  -*- C -*-
> +   This file is part of elfutils.
> +
> +   This file is free software; you can redistribute it and/or modify
> +   it under the terms of either
> +
> +     * the GNU Lesser General Public License as published by the Free
> +       Software Foundation; either version 3 of the License, or (at
> +       your option) any later version
> +
> +   or
> +
> +     * the GNU General Public License as published by the Free
> +       Software Foundation; either version 2 of the License, or (at
> +       your option) any later version
> +
> +   or both in parallel, as here.
> +
> +   elfutils 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
> +   General Public License for more details.
> +
> +   You should have received copies of the GNU General Public License and
> +   the GNU Lesser General Public License along with this program.  If
> +   not, see <http://www.gnu.org/licenses/>.  */
> +
> +/*         NAME,                       REL|EXEC|DYN    */
> +
> +RELOC_TYPE (NONE,                      EXEC|DYN)
> +RELOC_TYPE (32,                                REL|EXEC|DYN)
> +RELOC_TYPE (64,                                REL|EXEC|DYN)
> +RELOC_TYPE (RELATIVE,                  EXEC|DYN)
> +RELOC_TYPE (COPY,                      EXEC|DYN)
> +RELOC_TYPE (JUMP_SLOT,                 EXEC|DYN)
> +RELOC_TYPE (TLS_DTPMOD32,              EXEC|DYN)
> +RELOC_TYPE (TLS_DTPMOD64,              EXEC|DYN)
> +RELOC_TYPE (TLS_DTPREL32,              EXEC|DYN)
> +RELOC_TYPE (TLS_DTPREL64,              EXEC|DYN)
> +RELOC_TYPE (TLS_TPREL32,               EXEC|DYN)
> +RELOC_TYPE (TLS_TPREL64,               EXEC|DYN)
> +RELOC_TYPE (IRELATIVE,                 EXEC|DYN)
> +RELOC_TYPE (MARK_LA,                   REL)
> +RELOC_TYPE (MARK_PCREL,                        REL)
> +RELOC_TYPE (SOP_PUSH_PCREL,            REL)
> +RELOC_TYPE (SOP_PUSH_ABSOLUTE,         REL)
> +RELOC_TYPE (SOP_PUSH_DUP,              REL)
> +RELOC_TYPE (SOP_PUSH_GPREL,            REL)
> +RELOC_TYPE (SOP_PUSH_TLS_TPREL,                REL)
> +RELOC_TYPE (SOP_PUSH_TLS_GOT,          REL)
> +RELOC_TYPE (SOP_PUSH_TLS_GD,           REL)
> +RELOC_TYPE (SOP_PUSH_PLT_PCREL,                REL)
> +RELOC_TYPE (SOP_ASSERT,                        REL)
> +RELOC_TYPE (SOP_NOT,                   REL)
> +RELOC_TYPE (SOP_SUB,                   REL)
> +RELOC_TYPE (SOP_SL,                    REL)
> +RELOC_TYPE (SOP_SR,                    REL)
> +RELOC_TYPE (SOP_ADD,                   REL)
> +RELOC_TYPE (SOP_AND,                   REL)
> +RELOC_TYPE (SOP_IF_ELSE,               REL)
> +RELOC_TYPE (SOP_POP_32_S_10_5,         REL)
> +RELOC_TYPE (SOP_POP_32_U_10_12,                REL)
> +RELOC_TYPE (SOP_POP_32_S_10_12,                REL)
> +RELOC_TYPE (SOP_POP_32_S_10_16,                REL)
> +RELOC_TYPE (SOP_POP_32_S_10_16_S2,     REL)
> +RELOC_TYPE (SOP_POP_32_S_5_20,         REL)
> +RELOC_TYPE (SOP_POP_32_S_0_5_10_16_S2, REL)
> +RELOC_TYPE (SOP_POP_32_S_0_10_10_16_S2,        REL)
> +RELOC_TYPE (SOP_POP_32_U,              REL)
> +RELOC_TYPE (ADD8,                      REL)
> +RELOC_TYPE (ADD16,                     REL)
> +RELOC_TYPE (ADD24,                     REL)
> +RELOC_TYPE (ADD32,                     REL)
> +RELOC_TYPE (ADD64,                     REL)
> +RELOC_TYPE (SUB8,                      REL)
> +RELOC_TYPE (SUB16,                     REL)
> +RELOC_TYPE (SUB24,                     REL)
> +RELOC_TYPE (SUB32,                     REL)
> +RELOC_TYPE (SUB64,                     REL)
> +RELOC_TYPE (GNU_VTINHERIT,             REL)
> +RELOC_TYPE (GNU_VTENTRY,               REL)
> diff --git a/backends/loongarch_symbol.c b/backends/loongarch_symbol.c
> new file mode 100644
> index 00000000..8ba66a09
> --- /dev/null
> +++ b/backends/loongarch_symbol.c
> @@ -0,0 +1,74 @@
> +/* LoongArch specific symbolic name handling.
> +   Copyright (C) 2022 Hengqi Chen
> +   This file is part of elfutils.
> +
> +   This file is free software; you can redistribute it and/or modify
> +   it under the terms of either
> +
> +     * the GNU Lesser General Public License as published by the Free
> +       Software Foundation; either version 3 of the License, or (at
> +       your option) any later version
> +
> +   or
> +
> +     * the GNU General Public License as published by the Free
> +       Software Foundation; either version 2 of the License, or (at
> +       your option) any later version
> +
> +   or both in parallel, as here.
> +
> +   elfutils 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
> +   General Public License for more details.
> +
> +   You should have received copies of the GNU General Public License and
> +   the GNU Lesser General Public License along with this program.  If
> +   not, see <http://www.gnu.org/licenses/>.  */
> +
> +#ifdef HAVE_CONFIG_H
> +# include <config.h>
> +#endif
> +
> +#include <assert.h>
> +#include <elf.h>
> +#include <stddef.h>
> +#include <string.h>
> +
> +#define BACKEND loongarch_
> +#include "libebl_CPU.h"
> +
> +
> +/* Check for the simple reloc types.  */
> +Elf_Type
> +loongarch_reloc_simple_type (Ebl *ebl __attribute__ ((unused)), int type,
> +                            int *addsub)
> +{
> +  switch (type)
> +    {
> +    case R_LARCH_32:
> +      return ELF_T_WORD;
> +    case R_LARCH_64:
> +      return ELF_T_XWORD;
> +    case R_LARCH_ADD16:
> +      *addsub = 1;
> +      return ELF_T_HALF;
> +    case R_LARCH_ADD32:
> +      *addsub = 1;
> +      return ELF_T_WORD;
> +    case R_LARCH_ADD64:
> +      *addsub = 1;
> +      return ELF_T_XWORD;
> +    case R_LARCH_SUB16:
> +      *addsub = -1;
> +      return ELF_T_HALF;
> +    case R_LARCH_SUB32:
> +      *addsub = -1;
> +      return ELF_T_WORD;
> +    case R_LARCH_SUB64:
> +      *addsub = -1;
> +      return ELF_T_XWORD;
> +    default:
> +      return ELF_T_NUM;
> +    }
> +}
> diff --git a/libebl/ChangeLog b/libebl/ChangeLog
> index 6f55a5e7..5f9ea552 100644
> --- a/libebl/ChangeLog
> +++ b/libebl/ChangeLog
> @@ -1,3 +1,7 @@
> +2022-12-02  Hengqi Chen  <hengqi.chen@gmail.com>
> +
> +       * eblopenbackend.c (machines): Add entries for LoongArch.
> +
>  2022-10-21  Yonggang Luo  <luoyonggang@gmail.com>
>
>         * eblclosebackend.c: Remove dlfcn.h include.
> diff --git a/libebl/eblopenbackend.c b/libebl/eblopenbackend.c
> index 02f80653..b87aef19 100644
> --- a/libebl/eblopenbackend.c
> +++ b/libebl/eblopenbackend.c
> @@ -55,6 +55,7 @@ Ebl *m68k_init (Elf *, GElf_Half, Ebl *);
>  Ebl *bpf_init (Elf *, GElf_Half, Ebl *);
>  Ebl *riscv_init (Elf *, GElf_Half, Ebl *);
>  Ebl *csky_init (Elf *, GElf_Half, Ebl *);
> +Ebl *loongarch_init (Elf *, GElf_Half, Ebl *);
>
>  /* This table should contain the complete list of architectures as far
>     as the ELF specification is concerned.  */
> @@ -150,6 +151,7 @@ static const struct
>    { riscv_init, "elf_riscv", "riscv", 5, EM_RISCV, ELFCLASS64, ELFDATA2LSB },
>    { riscv_init, "elf_riscv", "riscv", 5, EM_RISCV, ELFCLASS32, ELFDATA2LSB },
>    { csky_init, "elf_csky", "csky", 4, EM_CSKY, ELFCLASS32, ELFDATA2LSB },
> +  { loongarch_init, "elf_loongarch", "loongarch", 9, EM_LOONGARCH, ELFCLASS64, ELFDATA2LSB },
>  };
>  #define nmachines (sizeof (machines) / sizeof (machines[0]))
>
> diff --git a/src/ChangeLog b/src/ChangeLog
> index 66428b70..b679f092 100644
> --- a/src/ChangeLog
> +++ b/src/ChangeLog
> @@ -1,3 +1,7 @@
> +2022-12-02  Hengqi Chen  <hengqi.chen@gmail.com>
> +
> +       * elflint.c (valid_e_machine): Add EM_LOONGARCH.
> +
>  2022-11-03  Mark Wielaard  <mark@klomp.org>
>
>         * readelf.c (get_dynscn_addrs): Check gelf_getdyn doesn't
> diff --git a/src/elflint.c b/src/elflint.c
> index 565cffdc..b9548862 100644
> --- a/src/elflint.c
> +++ b/src/elflint.c
> @@ -329,7 +329,7 @@ static const int valid_e_machine[] =
>      EM_CRIS, EM_JAVELIN, EM_FIREPATH, EM_ZSP, EM_MMIX, EM_HUANY, EM_PRISM,
>      EM_AVR, EM_FR30, EM_D10V, EM_D30V, EM_V850, EM_M32R, EM_MN10300,
>      EM_MN10200, EM_PJ, EM_OPENRISC, EM_ARC_A5, EM_XTENSA, EM_ALPHA,
> -    EM_TILEGX, EM_TILEPRO, EM_AARCH64, EM_BPF, EM_RISCV, EM_CSKY
> +    EM_TILEGX, EM_TILEPRO, EM_AARCH64, EM_BPF, EM_RISCV, EM_CSKY, EM_LOONGARCH,
>    };
>  #define nvalid_e_machine \
>    (sizeof (valid_e_machine) / sizeof (valid_e_machine[0]))
> --
> 2.37.3
>
  
Mark Wielaard Dec. 19, 2022, 11:06 p.m. UTC | #2
Hi,

On Sat, Dec 03, 2022 at 09:47:07PM +0800, Hengqi Chen via Elfutils-devel wrote:
> This implements initial support for the LoongArch architecture.
> 
> Signed-off-by: Hengqi Chen <hengqi.chen@gmail.com>
> ---
>  backends/ChangeLog           |  7 ++++
>  backends/Makefile.am         |  7 +++-
>  backends/loongarch_init.c    | 50 ++++++++++++++++++++++
>  backends/loongarch_reloc.def | 81 ++++++++++++++++++++++++++++++++++++
>  backends/loongarch_symbol.c  | 74 ++++++++++++++++++++++++++++++++
>  libebl/ChangeLog             |  4 ++
>  libebl/eblopenbackend.c      |  2 +
>  src/ChangeLog                |  4 ++
>  src/elflint.c                |  2 +-
>  9 files changed, 228 insertions(+), 3 deletions(-)
>  create mode 100644 backends/loongarch_init.c
>  create mode 100644 backends/loongarch_reloc.def
>  create mode 100644 backends/loongarch_symbol.c
> 
> diff --git a/backends/ChangeLog b/backends/ChangeLog
> index 5b0daffe..5813ddcc 100644
> --- a/backends/ChangeLog
> +++ b/backends/ChangeLog
> @@ -1,3 +1,10 @@
> +2022-12-02  Hengqi Chen  <hengqi.chen@gmail.com>
> +
> +	* Makefile.am (modules): Add loongarch.
> +	* loongarch_init.c: New file.
> +	* loongarch_reloc.def: New file.
> +	* loongarch_symbol.c: New file.
> +
>  2022-08-09  Andreas Schwab  <schwab@suse.de>
>  
>  	* riscv_init.c (riscv_init): HOOK segment_type_name,
> diff --git a/backends/Makefile.am b/backends/Makefile.am
> index 9566377f..0824123d 100644
> --- a/backends/Makefile.am
> +++ b/backends/Makefile.am
> @@ -37,7 +37,7 @@ AM_CPPFLAGS += -I$(top_srcdir)/libebl -I$(top_srcdir)/libasm \
>  noinst_LIBRARIES = libebl_backends.a libebl_backends_pic.a
>  
>  modules = i386 sh x86_64 ia64 alpha arm aarch64 sparc ppc ppc64 s390 \
> -	  m68k bpf riscv csky
> +	  m68k bpf riscv csky loongarch
>  
>  i386_SRCS = i386_init.c i386_symbol.c i386_corenote.c i386_cfi.c \
>  	    i386_retval.c i386_regs.c i386_auxv.c \
> @@ -96,11 +96,14 @@ riscv_SRCS = riscv_init.c riscv_symbol.c riscv_cfi.c riscv_regs.c \
>  csky_SRCS = csky_attrs.c csky_init.c csky_symbol.c csky_cfi.c \
>  	    csky_regs.c csky_initreg.c csky_corenote.c
>  
> +loongarch_SRCS = loongarch_init.c loongarch_symbol.c
> +
>  libebl_backends_a_SOURCES = $(i386_SRCS) $(sh_SRCS) $(x86_64_SRCS) \
>  			    $(ia64_SRCS) $(alpha_SRCS) $(arm_SRCS) \
>  			    $(aarch64_SRCS) $(sparc_SRCS) $(ppc_SRCS) \
>  			    $(ppc64_SRCS) $(s390_SRCS) \
> -			    $(m68k_SRCS) $(bpf_SRCS) $(riscv_SRCS) $(csky_SRCS)
> +			    $(m68k_SRCS) $(bpf_SRCS) $(riscv_SRCS) $(csky_SRCS) \
> +			    $(loongarch_SRCS)
>  
>  libebl_backends_pic_a_SOURCES =
>  am_libebl_backends_pic_a_OBJECTS = $(libebl_backends_a_SOURCES:.c=.os)

OK. And the def file get into EXTRA_DIST through the
$(modules:=_reloc.def) rule.

> diff --git a/backends/loongarch_init.c b/backends/loongarch_init.c
> new file mode 100644
> index 00000000..a8ed9e81
> --- /dev/null
> +++ b/backends/loongarch_init.c
> @@ -0,0 +1,50 @@
> +/* Initialization of LoongArch specific backend library.
> +   Copyright (C) 2022 Hengqi Chen
> +   This file is part of elfutils.
> +
> +   This file is free software; you can redistribute it and/or modify
> +   it under the terms of either
> +
> +     * the GNU Lesser General Public License as published by the Free
> +       Software Foundation; either version 3 of the License, or (at
> +       your option) any later version
> +
> +   or
> +
> +     * the GNU General Public License as published by the Free
> +       Software Foundation; either version 2 of the License, or (at
> +       your option) any later version
> +
> +   or both in parallel, as here.
> +
> +   elfutils 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
> +   General Public License for more details.
> +
> +   You should have received copies of the GNU General Public License and
> +   the GNU Lesser General Public License along with this program.  If
> +   not, see <http://www.gnu.org/licenses/>.  */
> +
> +#ifdef HAVE_CONFIG_H
> +# include <config.h>
> +#endif
> +
> +#define BACKEND		loongarch_
> +#define RELOC_PREFIX	R_LARCH_
> +#include "libebl_CPU.h"
> +
> +/* This defines the common reloc hooks based on loongarch_reloc.def.  */
> +#include "common-reloc.c"
> +
> +
> +Ebl *
> +loongarch_init (Elf *elf __attribute__ ((unused)),
> +	        GElf_Half machine __attribute__ ((unused)),
> +	        Ebl *eh)
> +{
> +  loongarch_init_reloc (eh);
> +  HOOK (eh, reloc_simple_type);
> +
> +  return eh;
> +}

OK, this is the minimal backend definition if all you need is debug
section relocations to work for ET_REL files.

> diff --git a/backends/loongarch_reloc.def b/backends/loongarch_reloc.def
> new file mode 100644
> index 00000000..dd4a6b6d
> --- /dev/null
> +++ b/backends/loongarch_reloc.def
> @@ -0,0 +1,81 @@
> +/* List the relocation types for LoongArch.  -*- C -*-
> +   This file is part of elfutils.
> +
> +   This file is free software; you can redistribute it and/or modify
> +   it under the terms of either
> +
> +     * the GNU Lesser General Public License as published by the Free
> +       Software Foundation; either version 3 of the License, or (at
> +       your option) any later version
> +
> +   or
> +
> +     * the GNU General Public License as published by the Free
> +       Software Foundation; either version 2 of the License, or (at
> +       your option) any later version
> +
> +   or both in parallel, as here.
> +
> +   elfutils 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
> +   General Public License for more details.
> +
> +   You should have received copies of the GNU General Public License and
> +   the GNU Lesser General Public License along with this program.  If
> +   not, see <http://www.gnu.org/licenses/>.  */
> +
> +/*	    NAME,			REL|EXEC|DYN	*/
> +
> +RELOC_TYPE (NONE,			EXEC|DYN)
> +RELOC_TYPE (32,				REL|EXEC|DYN)
> +RELOC_TYPE (64,				REL|EXEC|DYN)
> +RELOC_TYPE (RELATIVE,			EXEC|DYN)
> +RELOC_TYPE (COPY,			EXEC|DYN)
> +RELOC_TYPE (JUMP_SLOT,			EXEC|DYN)
> +RELOC_TYPE (TLS_DTPMOD32,		EXEC|DYN)
> +RELOC_TYPE (TLS_DTPMOD64,		EXEC|DYN)
> +RELOC_TYPE (TLS_DTPREL32,		EXEC|DYN)
> +RELOC_TYPE (TLS_DTPREL64,		EXEC|DYN)
> +RELOC_TYPE (TLS_TPREL32,		EXEC|DYN)
> +RELOC_TYPE (TLS_TPREL64,		EXEC|DYN)
> +RELOC_TYPE (IRELATIVE,			EXEC|DYN)
> +RELOC_TYPE (MARK_LA,			REL)
> +RELOC_TYPE (MARK_PCREL,			REL)
> +RELOC_TYPE (SOP_PUSH_PCREL,		REL)
> +RELOC_TYPE (SOP_PUSH_ABSOLUTE,		REL)
> +RELOC_TYPE (SOP_PUSH_DUP,		REL)
> +RELOC_TYPE (SOP_PUSH_GPREL,		REL)
> +RELOC_TYPE (SOP_PUSH_TLS_TPREL,		REL)
> +RELOC_TYPE (SOP_PUSH_TLS_GOT,		REL)
> +RELOC_TYPE (SOP_PUSH_TLS_GD,		REL)
> +RELOC_TYPE (SOP_PUSH_PLT_PCREL,		REL)
> +RELOC_TYPE (SOP_ASSERT,			REL)
> +RELOC_TYPE (SOP_NOT,			REL)
> +RELOC_TYPE (SOP_SUB,			REL)
> +RELOC_TYPE (SOP_SL,			REL)
> +RELOC_TYPE (SOP_SR,			REL)
> +RELOC_TYPE (SOP_ADD,			REL)
> +RELOC_TYPE (SOP_AND,			REL)
> +RELOC_TYPE (SOP_IF_ELSE,		REL)
> +RELOC_TYPE (SOP_POP_32_S_10_5,		REL)
> +RELOC_TYPE (SOP_POP_32_U_10_12,		REL)
> +RELOC_TYPE (SOP_POP_32_S_10_12,		REL)
> +RELOC_TYPE (SOP_POP_32_S_10_16,		REL)
> +RELOC_TYPE (SOP_POP_32_S_10_16_S2,	REL)
> +RELOC_TYPE (SOP_POP_32_S_5_20,		REL)
> +RELOC_TYPE (SOP_POP_32_S_0_5_10_16_S2,	REL)
> +RELOC_TYPE (SOP_POP_32_S_0_10_10_16_S2,	REL)
> +RELOC_TYPE (SOP_POP_32_U,		REL)
> +RELOC_TYPE (ADD8,			REL)
> +RELOC_TYPE (ADD16,			REL)
> +RELOC_TYPE (ADD24,			REL)
> +RELOC_TYPE (ADD32,			REL)
> +RELOC_TYPE (ADD64,			REL)
> +RELOC_TYPE (SUB8,			REL)
> +RELOC_TYPE (SUB16,			REL)
> +RELOC_TYPE (SUB24,			REL)
> +RELOC_TYPE (SUB32,			REL)
> +RELOC_TYPE (SUB64,			REL)
> +RELOC_TYPE (GNU_VTINHERIT,		REL)
> +RELOC_TYPE (GNU_VTENTRY,		REL)

I asssume these are correct. If there is a reference to the loongarch
ELF spec it would be nice to include that in a comment.

> diff --git a/backends/loongarch_symbol.c b/backends/loongarch_symbol.c
> new file mode 100644
> index 00000000..8ba66a09
> --- /dev/null
> +++ b/backends/loongarch_symbol.c
> @@ -0,0 +1,74 @@
> +/* LoongArch specific symbolic name handling.
> +   Copyright (C) 2022 Hengqi Chen
> +   This file is part of elfutils.
> +
> +   This file is free software; you can redistribute it and/or modify
> +   it under the terms of either
> +
> +     * the GNU Lesser General Public License as published by the Free
> +       Software Foundation; either version 3 of the License, or (at
> +       your option) any later version
> +
> +   or
> +
> +     * the GNU General Public License as published by the Free
> +       Software Foundation; either version 2 of the License, or (at
> +       your option) any later version
> +
> +   or both in parallel, as here.
> +
> +   elfutils 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
> +   General Public License for more details.
> +
> +   You should have received copies of the GNU General Public License and
> +   the GNU Lesser General Public License along with this program.  If
> +   not, see <http://www.gnu.org/licenses/>.  */
> +
> +#ifdef HAVE_CONFIG_H
> +# include <config.h>
> +#endif
> +
> +#include <assert.h>
> +#include <elf.h>
> +#include <stddef.h>
> +#include <string.h>
> +
> +#define BACKEND loongarch_
> +#include "libebl_CPU.h"
> +
> +
> +/* Check for the simple reloc types.  */
> +Elf_Type
> +loongarch_reloc_simple_type (Ebl *ebl __attribute__ ((unused)), int type,
> +			     int *addsub)
> +{
> +  switch (type)
> +    {
> +    case R_LARCH_32:
> +      return ELF_T_WORD;
> +    case R_LARCH_64:
> +      return ELF_T_XWORD;
> +    case R_LARCH_ADD16:
> +      *addsub = 1;
> +      return ELF_T_HALF;
> +    case R_LARCH_ADD32:
> +      *addsub = 1;
> +      return ELF_T_WORD;
> +    case R_LARCH_ADD64:
> +      *addsub = 1;
> +      return ELF_T_XWORD;
> +    case R_LARCH_SUB16:
> +      *addsub = -1;
> +      return ELF_T_HALF;
> +    case R_LARCH_SUB32:
> +      *addsub = -1;
> +      return ELF_T_WORD;
> +    case R_LARCH_SUB64:
> +      *addsub = -1;
> +      return ELF_T_XWORD;
> +    default:
> +      return ELF_T_NUM;
> +    }
> +}

Nice, full set of simple relocations.

> diff --git a/libebl/ChangeLog b/libebl/ChangeLog
> index 6f55a5e7..5f9ea552 100644
> --- a/libebl/ChangeLog
> +++ b/libebl/ChangeLog
> @@ -1,3 +1,7 @@
> +2022-12-02  Hengqi Chen  <hengqi.chen@gmail.com>
> +
> +	* eblopenbackend.c (machines): Add entries for LoongArch.
> +
>  2022-10-21  Yonggang Luo  <luoyonggang@gmail.com>
>  
>  	* eblclosebackend.c: Remove dlfcn.h include.
> diff --git a/libebl/eblopenbackend.c b/libebl/eblopenbackend.c
> index 02f80653..b87aef19 100644
> --- a/libebl/eblopenbackend.c
> +++ b/libebl/eblopenbackend.c
> @@ -55,6 +55,7 @@ Ebl *m68k_init (Elf *, GElf_Half, Ebl *);
>  Ebl *bpf_init (Elf *, GElf_Half, Ebl *);
>  Ebl *riscv_init (Elf *, GElf_Half, Ebl *);
>  Ebl *csky_init (Elf *, GElf_Half, Ebl *);
> +Ebl *loongarch_init (Elf *, GElf_Half, Ebl *);
>  
>  /* This table should contain the complete list of architectures as far
>     as the ELF specification is concerned.  */
> @@ -150,6 +151,7 @@ static const struct
>    { riscv_init, "elf_riscv", "riscv", 5, EM_RISCV, ELFCLASS64, ELFDATA2LSB },
>    { riscv_init, "elf_riscv", "riscv", 5, EM_RISCV, ELFCLASS32, ELFDATA2LSB },
>    { csky_init, "elf_csky", "csky", 4, EM_CSKY, ELFCLASS32, ELFDATA2LSB },
> +  { loongarch_init, "elf_loongarch", "loongarch", 9, EM_LOONGARCH, ELFCLASS64, ELFDATA2LSB },
>  };
>  #define nmachines (sizeof (machines) / sizeof (machines[0]))

OK.

> diff --git a/src/ChangeLog b/src/ChangeLog
> index 66428b70..b679f092 100644
> --- a/src/ChangeLog
> +++ b/src/ChangeLog
> @@ -1,3 +1,7 @@
> +2022-12-02  Hengqi Chen  <hengqi.chen@gmail.com>
> +
> +	* elflint.c (valid_e_machine): Add EM_LOONGARCH.
> +
>  2022-11-03  Mark Wielaard  <mark@klomp.org>
>  
>  	* readelf.c (get_dynscn_addrs): Check gelf_getdyn doesn't
> diff --git a/src/elflint.c b/src/elflint.c
> index 565cffdc..b9548862 100644
> --- a/src/elflint.c
> +++ b/src/elflint.c
> @@ -329,7 +329,7 @@ static const int valid_e_machine[] =
>      EM_CRIS, EM_JAVELIN, EM_FIREPATH, EM_ZSP, EM_MMIX, EM_HUANY, EM_PRISM,
>      EM_AVR, EM_FR30, EM_D10V, EM_D30V, EM_V850, EM_M32R, EM_MN10300,
>      EM_MN10200, EM_PJ, EM_OPENRISC, EM_ARC_A5, EM_XTENSA, EM_ALPHA,
> -    EM_TILEGX, EM_TILEPRO, EM_AARCH64, EM_BPF, EM_RISCV, EM_CSKY
> +    EM_TILEGX, EM_TILEPRO, EM_AARCH64, EM_BPF, EM_RISCV, EM_CSKY, EM_LOONGARCH,
>    };
>  #define nvalid_e_machine \
>    (sizeof (valid_e_machine) / sizeof (valid_e_machine[0]))

And with this I assume elflint now works for a native binary?

The patch itself looks good. So I pushed it.

But to get a full (native) make check pass on longaarch a few more
backend hooks are probably needed. What is the current result of make
check on a native longaarch build?

Also to make sure it is/can be tested on other arches it might make
sense to add a testcase. See tests/run-strip-reloc.sh how to create a
small loongarch linux kernel module and test that relocation (and
stripping) works.

Cheers,

Mark
  

Patch

diff --git a/backends/ChangeLog b/backends/ChangeLog
index 5b0daffe..5813ddcc 100644
--- a/backends/ChangeLog
+++ b/backends/ChangeLog
@@ -1,3 +1,10 @@ 
+2022-12-02  Hengqi Chen  <hengqi.chen@gmail.com>
+
+	* Makefile.am (modules): Add loongarch.
+	* loongarch_init.c: New file.
+	* loongarch_reloc.def: New file.
+	* loongarch_symbol.c: New file.
+
 2022-08-09  Andreas Schwab  <schwab@suse.de>
 
 	* riscv_init.c (riscv_init): HOOK segment_type_name,
diff --git a/backends/Makefile.am b/backends/Makefile.am
index 9566377f..0824123d 100644
--- a/backends/Makefile.am
+++ b/backends/Makefile.am
@@ -37,7 +37,7 @@  AM_CPPFLAGS += -I$(top_srcdir)/libebl -I$(top_srcdir)/libasm \
 noinst_LIBRARIES = libebl_backends.a libebl_backends_pic.a
 
 modules = i386 sh x86_64 ia64 alpha arm aarch64 sparc ppc ppc64 s390 \
-	  m68k bpf riscv csky
+	  m68k bpf riscv csky loongarch
 
 i386_SRCS = i386_init.c i386_symbol.c i386_corenote.c i386_cfi.c \
 	    i386_retval.c i386_regs.c i386_auxv.c \
@@ -96,11 +96,14 @@  riscv_SRCS = riscv_init.c riscv_symbol.c riscv_cfi.c riscv_regs.c \
 csky_SRCS = csky_attrs.c csky_init.c csky_symbol.c csky_cfi.c \
 	    csky_regs.c csky_initreg.c csky_corenote.c
 
+loongarch_SRCS = loongarch_init.c loongarch_symbol.c
+
 libebl_backends_a_SOURCES = $(i386_SRCS) $(sh_SRCS) $(x86_64_SRCS) \
 			    $(ia64_SRCS) $(alpha_SRCS) $(arm_SRCS) \
 			    $(aarch64_SRCS) $(sparc_SRCS) $(ppc_SRCS) \
 			    $(ppc64_SRCS) $(s390_SRCS) \
-			    $(m68k_SRCS) $(bpf_SRCS) $(riscv_SRCS) $(csky_SRCS)
+			    $(m68k_SRCS) $(bpf_SRCS) $(riscv_SRCS) $(csky_SRCS) \
+			    $(loongarch_SRCS)
 
 libebl_backends_pic_a_SOURCES =
 am_libebl_backends_pic_a_OBJECTS = $(libebl_backends_a_SOURCES:.c=.os)
diff --git a/backends/loongarch_init.c b/backends/loongarch_init.c
new file mode 100644
index 00000000..a8ed9e81
--- /dev/null
+++ b/backends/loongarch_init.c
@@ -0,0 +1,50 @@ 
+/* Initialization of LoongArch specific backend library.
+   Copyright (C) 2022 Hengqi Chen
+   This file is part of elfutils.
+
+   This file is free software; you can redistribute it and/or modify
+   it under the terms of either
+
+     * the GNU Lesser General Public License as published by the Free
+       Software Foundation; either version 3 of the License, or (at
+       your option) any later version
+
+   or
+
+     * the GNU General Public License as published by the Free
+       Software Foundation; either version 2 of the License, or (at
+       your option) any later version
+
+   or both in parallel, as here.
+
+   elfutils 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
+   General Public License for more details.
+
+   You should have received copies of the GNU General Public License and
+   the GNU Lesser General Public License along with this program.  If
+   not, see <http://www.gnu.org/licenses/>.  */
+
+#ifdef HAVE_CONFIG_H
+# include <config.h>
+#endif
+
+#define BACKEND		loongarch_
+#define RELOC_PREFIX	R_LARCH_
+#include "libebl_CPU.h"
+
+/* This defines the common reloc hooks based on loongarch_reloc.def.  */
+#include "common-reloc.c"
+
+
+Ebl *
+loongarch_init (Elf *elf __attribute__ ((unused)),
+	        GElf_Half machine __attribute__ ((unused)),
+	        Ebl *eh)
+{
+  loongarch_init_reloc (eh);
+  HOOK (eh, reloc_simple_type);
+
+  return eh;
+}
diff --git a/backends/loongarch_reloc.def b/backends/loongarch_reloc.def
new file mode 100644
index 00000000..dd4a6b6d
--- /dev/null
+++ b/backends/loongarch_reloc.def
@@ -0,0 +1,81 @@ 
+/* List the relocation types for LoongArch.  -*- C -*-
+   This file is part of elfutils.
+
+   This file is free software; you can redistribute it and/or modify
+   it under the terms of either
+
+     * the GNU Lesser General Public License as published by the Free
+       Software Foundation; either version 3 of the License, or (at
+       your option) any later version
+
+   or
+
+     * the GNU General Public License as published by the Free
+       Software Foundation; either version 2 of the License, or (at
+       your option) any later version
+
+   or both in parallel, as here.
+
+   elfutils 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
+   General Public License for more details.
+
+   You should have received copies of the GNU General Public License and
+   the GNU Lesser General Public License along with this program.  If
+   not, see <http://www.gnu.org/licenses/>.  */
+
+/*	    NAME,			REL|EXEC|DYN	*/
+
+RELOC_TYPE (NONE,			EXEC|DYN)
+RELOC_TYPE (32,				REL|EXEC|DYN)
+RELOC_TYPE (64,				REL|EXEC|DYN)
+RELOC_TYPE (RELATIVE,			EXEC|DYN)
+RELOC_TYPE (COPY,			EXEC|DYN)
+RELOC_TYPE (JUMP_SLOT,			EXEC|DYN)
+RELOC_TYPE (TLS_DTPMOD32,		EXEC|DYN)
+RELOC_TYPE (TLS_DTPMOD64,		EXEC|DYN)
+RELOC_TYPE (TLS_DTPREL32,		EXEC|DYN)
+RELOC_TYPE (TLS_DTPREL64,		EXEC|DYN)
+RELOC_TYPE (TLS_TPREL32,		EXEC|DYN)
+RELOC_TYPE (TLS_TPREL64,		EXEC|DYN)
+RELOC_TYPE (IRELATIVE,			EXEC|DYN)
+RELOC_TYPE (MARK_LA,			REL)
+RELOC_TYPE (MARK_PCREL,			REL)
+RELOC_TYPE (SOP_PUSH_PCREL,		REL)
+RELOC_TYPE (SOP_PUSH_ABSOLUTE,		REL)
+RELOC_TYPE (SOP_PUSH_DUP,		REL)
+RELOC_TYPE (SOP_PUSH_GPREL,		REL)
+RELOC_TYPE (SOP_PUSH_TLS_TPREL,		REL)
+RELOC_TYPE (SOP_PUSH_TLS_GOT,		REL)
+RELOC_TYPE (SOP_PUSH_TLS_GD,		REL)
+RELOC_TYPE (SOP_PUSH_PLT_PCREL,		REL)
+RELOC_TYPE (SOP_ASSERT,			REL)
+RELOC_TYPE (SOP_NOT,			REL)
+RELOC_TYPE (SOP_SUB,			REL)
+RELOC_TYPE (SOP_SL,			REL)
+RELOC_TYPE (SOP_SR,			REL)
+RELOC_TYPE (SOP_ADD,			REL)
+RELOC_TYPE (SOP_AND,			REL)
+RELOC_TYPE (SOP_IF_ELSE,		REL)
+RELOC_TYPE (SOP_POP_32_S_10_5,		REL)
+RELOC_TYPE (SOP_POP_32_U_10_12,		REL)
+RELOC_TYPE (SOP_POP_32_S_10_12,		REL)
+RELOC_TYPE (SOP_POP_32_S_10_16,		REL)
+RELOC_TYPE (SOP_POP_32_S_10_16_S2,	REL)
+RELOC_TYPE (SOP_POP_32_S_5_20,		REL)
+RELOC_TYPE (SOP_POP_32_S_0_5_10_16_S2,	REL)
+RELOC_TYPE (SOP_POP_32_S_0_10_10_16_S2,	REL)
+RELOC_TYPE (SOP_POP_32_U,		REL)
+RELOC_TYPE (ADD8,			REL)
+RELOC_TYPE (ADD16,			REL)
+RELOC_TYPE (ADD24,			REL)
+RELOC_TYPE (ADD32,			REL)
+RELOC_TYPE (ADD64,			REL)
+RELOC_TYPE (SUB8,			REL)
+RELOC_TYPE (SUB16,			REL)
+RELOC_TYPE (SUB24,			REL)
+RELOC_TYPE (SUB32,			REL)
+RELOC_TYPE (SUB64,			REL)
+RELOC_TYPE (GNU_VTINHERIT,		REL)
+RELOC_TYPE (GNU_VTENTRY,		REL)
diff --git a/backends/loongarch_symbol.c b/backends/loongarch_symbol.c
new file mode 100644
index 00000000..8ba66a09
--- /dev/null
+++ b/backends/loongarch_symbol.c
@@ -0,0 +1,74 @@ 
+/* LoongArch specific symbolic name handling.
+   Copyright (C) 2022 Hengqi Chen
+   This file is part of elfutils.
+
+   This file is free software; you can redistribute it and/or modify
+   it under the terms of either
+
+     * the GNU Lesser General Public License as published by the Free
+       Software Foundation; either version 3 of the License, or (at
+       your option) any later version
+
+   or
+
+     * the GNU General Public License as published by the Free
+       Software Foundation; either version 2 of the License, or (at
+       your option) any later version
+
+   or both in parallel, as here.
+
+   elfutils 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
+   General Public License for more details.
+
+   You should have received copies of the GNU General Public License and
+   the GNU Lesser General Public License along with this program.  If
+   not, see <http://www.gnu.org/licenses/>.  */
+
+#ifdef HAVE_CONFIG_H
+# include <config.h>
+#endif
+
+#include <assert.h>
+#include <elf.h>
+#include <stddef.h>
+#include <string.h>
+
+#define BACKEND loongarch_
+#include "libebl_CPU.h"
+
+
+/* Check for the simple reloc types.  */
+Elf_Type
+loongarch_reloc_simple_type (Ebl *ebl __attribute__ ((unused)), int type,
+			     int *addsub)
+{
+  switch (type)
+    {
+    case R_LARCH_32:
+      return ELF_T_WORD;
+    case R_LARCH_64:
+      return ELF_T_XWORD;
+    case R_LARCH_ADD16:
+      *addsub = 1;
+      return ELF_T_HALF;
+    case R_LARCH_ADD32:
+      *addsub = 1;
+      return ELF_T_WORD;
+    case R_LARCH_ADD64:
+      *addsub = 1;
+      return ELF_T_XWORD;
+    case R_LARCH_SUB16:
+      *addsub = -1;
+      return ELF_T_HALF;
+    case R_LARCH_SUB32:
+      *addsub = -1;
+      return ELF_T_WORD;
+    case R_LARCH_SUB64:
+      *addsub = -1;
+      return ELF_T_XWORD;
+    default:
+      return ELF_T_NUM;
+    }
+}
diff --git a/libebl/ChangeLog b/libebl/ChangeLog
index 6f55a5e7..5f9ea552 100644
--- a/libebl/ChangeLog
+++ b/libebl/ChangeLog
@@ -1,3 +1,7 @@ 
+2022-12-02  Hengqi Chen  <hengqi.chen@gmail.com>
+
+	* eblopenbackend.c (machines): Add entries for LoongArch.
+
 2022-10-21  Yonggang Luo  <luoyonggang@gmail.com>
 
 	* eblclosebackend.c: Remove dlfcn.h include.
diff --git a/libebl/eblopenbackend.c b/libebl/eblopenbackend.c
index 02f80653..b87aef19 100644
--- a/libebl/eblopenbackend.c
+++ b/libebl/eblopenbackend.c
@@ -55,6 +55,7 @@  Ebl *m68k_init (Elf *, GElf_Half, Ebl *);
 Ebl *bpf_init (Elf *, GElf_Half, Ebl *);
 Ebl *riscv_init (Elf *, GElf_Half, Ebl *);
 Ebl *csky_init (Elf *, GElf_Half, Ebl *);
+Ebl *loongarch_init (Elf *, GElf_Half, Ebl *);
 
 /* This table should contain the complete list of architectures as far
    as the ELF specification is concerned.  */
@@ -150,6 +151,7 @@  static const struct
   { riscv_init, "elf_riscv", "riscv", 5, EM_RISCV, ELFCLASS64, ELFDATA2LSB },
   { riscv_init, "elf_riscv", "riscv", 5, EM_RISCV, ELFCLASS32, ELFDATA2LSB },
   { csky_init, "elf_csky", "csky", 4, EM_CSKY, ELFCLASS32, ELFDATA2LSB },
+  { loongarch_init, "elf_loongarch", "loongarch", 9, EM_LOONGARCH, ELFCLASS64, ELFDATA2LSB },
 };
 #define nmachines (sizeof (machines) / sizeof (machines[0]))
 
diff --git a/src/ChangeLog b/src/ChangeLog
index 66428b70..b679f092 100644
--- a/src/ChangeLog
+++ b/src/ChangeLog
@@ -1,3 +1,7 @@ 
+2022-12-02  Hengqi Chen  <hengqi.chen@gmail.com>
+
+	* elflint.c (valid_e_machine): Add EM_LOONGARCH.
+
 2022-11-03  Mark Wielaard  <mark@klomp.org>
 
 	* readelf.c (get_dynscn_addrs): Check gelf_getdyn doesn't
diff --git a/src/elflint.c b/src/elflint.c
index 565cffdc..b9548862 100644
--- a/src/elflint.c
+++ b/src/elflint.c
@@ -329,7 +329,7 @@  static const int valid_e_machine[] =
     EM_CRIS, EM_JAVELIN, EM_FIREPATH, EM_ZSP, EM_MMIX, EM_HUANY, EM_PRISM,
     EM_AVR, EM_FR30, EM_D10V, EM_D30V, EM_V850, EM_M32R, EM_MN10300,
     EM_MN10200, EM_PJ, EM_OPENRISC, EM_ARC_A5, EM_XTENSA, EM_ALPHA,
-    EM_TILEGX, EM_TILEPRO, EM_AARCH64, EM_BPF, EM_RISCV, EM_CSKY
+    EM_TILEGX, EM_TILEPRO, EM_AARCH64, EM_BPF, EM_RISCV, EM_CSKY, EM_LOONGARCH,
   };
 #define nvalid_e_machine \
   (sizeof (valid_e_machine) / sizeof (valid_e_machine[0]))