mailing list of musl libc
 help / color / mirror / code / Atom feed
* Re: [musl] Port the new architecture loongarch64 to musl
       [not found] <5f6d09a5.c3a.179460eee20.Coremail.zhaixiaojuan@loongson.cn>
@ 2021-05-07 21:58 ` Arnd Bergmann
  2021-05-08  5:16   ` 翟小娟
       [not found] ` <32e9f7ee-bd3c-762a-a771-2da41a8c1bb0@dereferenced.org>
       [not found] ` <CAE2XoE_9sQrizuiy0afA1dQdPxgOkPda_39oB9DOJN1c2FB0Cw@mail.gmail.com>
  2 siblings, 1 reply; 14+ messages in thread
From: Arnd Bergmann @ 2021-05-07 21:58 UTC (permalink / raw)
  To: musl; +Cc: 陈国祺

On Fri, May 7, 2021 at 11:01 AM 翟小娟 <zhaixiaojuan@loongson.cn> wrote:
>
> Hi,
> I ported a new architecture loongarch64 on the latest branch of musl master. It has been successfully compiled and run the official test libraries libc-testsuit and libc-test of musl.
> The source code of the prot has been published in https://github.com/loongson-community/musl.  Or check the attachment 0001-port-to-loongarch64.patch, it is the transplanted patch file.

It's nice to see upstreaming work for loongarch64.

I'm mainly interested in the kernel side of this, as I review any new
ports of Linux
to new architectures.

Looking at the system call interfaces, I see that you used the generic ABI,
so there is a good chance that this will not require incompatible changes,
but a proper review of the kernel port will be necessary to be sure.

I did notice that the system call list is a bit outdated and does not
reflect the
latest kernel, but that should be easy to change. There are a few system calls
that are technically obsoleted by newer variants now, and we may decide to
drop them for new architectures in favor of the newer variants, e.g. openat,
faccessat, and io_getevents.

The order I would generally recommend for upstreaming is:

1. toolchain (either gcc/binutils or clang)
2. kernel
3. libc
4. everything else

If you do the order differently, there is a risk that ABI changes in one of the
lower levels require changing the upper levels later on.

        Arnd

^ permalink raw reply	[flat|nested] 14+ messages in thread

* Re: Re: [musl] Port the new architecture loongarch64 to musl
  2021-05-07 21:58 ` [musl] Port the new architecture loongarch64 to musl Arnd Bergmann
@ 2021-05-08  5:16   ` 翟小娟
  2021-05-09  7:56     ` Arnd Bergmann
  0 siblings, 1 reply; 14+ messages in thread
From: 翟小娟 @ 2021-05-08  5:16 UTC (permalink / raw)
  To: musl; +Cc: 陈国祺

Yes, we are still using faccessat on the kernel. After the kernel is updated later, we will eliminate these system calls in the musl source code.
We have already adapted the tool chain, libc, kernel and qemu source code. To ensure quality, we are currently undergoing further testing and verification. We plan to start submitting to the community next month. If necessary, we can provide a physical machine or qemu.


&gt; -----原始邮件-----
&gt; 发件人: "Arnd Bergmann" <arnd@kernel.org>
&gt; 发送时间: 2021-05-08 05:58:15 (星期六)
&gt; 收件人: musl@lists.openwall.com
&gt; 抄送: "陈国祺" <chenguoqi@loongson.cn>
&gt; 主题: Re: [musl] Port the new architecture loongarch64 to musl
&gt; 
&gt; On Fri, May 7, 2021 at 11:01 AM 翟小娟 <zhaixiaojuan@loongson.cn> wrote:
&gt; &gt;
&gt; &gt; Hi,
&gt; &gt; I ported a new architecture loongarch64 on the latest branch of musl master. It has been successfully compiled and run the official test libraries libc-testsuit and libc-test of musl.
&gt; &gt; The source code of the prot has been published in https://github.com/loongson-community/musl.  Or check the attachment 0001-port-to-loongarch64.patch, it is the transplanted patch file.
&gt; 
&gt; It's nice to see upstreaming work for loongarch64.
&gt; 
&gt; I'm mainly interested in the kernel side of this, as I review any new
&gt; ports of Linux
&gt; to new architectures.
&gt; 
&gt; Looking at the system call interfaces, I see that you used the generic ABI,
&gt; so there is a good chance that this will not require incompatible changes,
&gt; but a proper review of the kernel port will be necessary to be sure.
&gt; 
&gt; I did notice that the system call list is a bit outdated and does not
&gt; reflect the
&gt; latest kernel, but that should be easy to change. There are a few system calls
&gt; that are technically obsoleted by newer variants now, and we may decide to
&gt; drop them for new architectures in favor of the newer variants, e.g. openat,
&gt; faccessat, and io_getevents.
&gt; 
&gt; The order I would generally recommend for upstreaming is:
&gt; 
&gt; 1. toolchain (either gcc/binutils or clang)
&gt; 2. kernel
&gt; 3. libc
&gt; 4. everything else
&gt; 
&gt; If you do the order differently, there is a risk that ABI changes in one of the
&gt; lower levels require changing the upper levels later on.
&gt; 
&gt;         Arnd
</zhaixiaojuan@loongson.cn></chenguoqi@loongson.cn></arnd@kernel.org>

^ permalink raw reply	[flat|nested] 14+ messages in thread

* Re: Re: [musl] Port the new architecture loongarch64 to musl
       [not found] ` <CAE2XoE_9sQrizuiy0afA1dQdPxgOkPda_39oB9DOJN1c2FB0Cw@mail.gmail.com>
@ 2021-05-08  5:18   ` 翟小娟
  2021-06-24 11:43   ` 翟小娟
  1 sibling, 0 replies; 14+ messages in thread
From: 翟小娟 @ 2021-05-08  5:18 UTC (permalink / raw)
  To: musl; +Cc: 陈国祺

Yes, we have ported loongarch64 qemu and plan to submit it to the community in June


-----原始邮件-----
发件人:"罗勇刚(Yonggang Luo)" <luoyonggang@gmail.com>
发送时间:2021-05-08 00:29:40 (星期六)
收件人: Musl <musl@lists.openwall.com>
抄送: "陈国祺" <chenguoqi@loongson.cn>
主题: Re: [musl] Port the new architecture loongarch64 to musl

Same question, does qemu have already support for  loongarch64, that's means a lot for auto testing
As the real hardware will be not broadly  available in the next few years.  
  
 

On Fri, May 7, 2021 at 5:01 PM 翟小娟 <zhaixiaojuan@loongson.cn> wrote:
Hi,
I ported a new architecture loongarch64 on the latest branch of musl master. It has been successfully compiled and run the official test libraries libc-testsuit and libc-test of musl.
The source code of the prot has been published in https://github.com/loongson-community/musl.  Or check the attachment 0001-port-to-loongarch64.patch, it is the transplanted patch file.

Introduction to loongarch architecture:
The Loongarch architecture is a simplified instruction computer style instruction system architecture. The instruction length is fixed and the encoding format is regular. Most instructions have only two source operands and one destination operand. The load/store architecture is adopted, that is, only load/store memory access instructions can access the memory, and the operation objects of other instructions are all It is the immediate value in the register or instruction code in the processor core.
The Loongson architecture is divided into two versions, 32bit and 64bit, called LA32 and LA64 respectively. LA64 architecture application level is downward binary compatible with LA32 architecture.



-- 
此致
礼
罗勇刚
Yours
sincerely,
Yonggang Luo


</zhaixiaojuan@loongson.cn></chenguoqi@loongson.cn></musl@lists.openwall.com></luoyonggang@gmail.com>

^ permalink raw reply	[flat|nested] 14+ messages in thread

* Re: Re: [musl] Port the new architecture loongarch64 to musl
       [not found] ` <32e9f7ee-bd3c-762a-a771-2da41a8c1bb0@dereferenced.org>
@ 2021-05-08  5:23   ` 翟小娟
  2021-05-08  7:49     ` Ariadne Conill
  0 siblings, 1 reply; 14+ messages in thread
From: 翟小娟 @ 2021-05-08  5:23 UTC (permalink / raw)
  To: musl; +Cc: 陈国祺

Yes, we refer to mips. 
qemu plans to submit to the community in the near future. For testing and verification, we can provide physical machines or qemu.


&gt; -----原始邮件-----
&gt; 发件人: "Ariadne Conill" <ariadne@dereferenced.org>
&gt; 发送时间: 2021-05-07 23:57:22 (星期五)
&gt; 收件人: musl@lists.openwall.com
&gt; 抄送: "陈国祺" <chenguoqi@loongson.cn>
&gt; 主题: Re: [musl] Port the new architecture loongarch64 to musl
&gt; 
&gt; Hello,
&gt; 
&gt; On Fri, 7 May 2021, 翟小娟 wrote:
&gt; 
&gt; &gt; Hi,
&gt; &gt; I ported a new architecture loongarch64 on the latest branch of musl master. It has been successfully compiled and run the official test libraries libc-testsuit and libc-test of musl.
&gt; &gt; The source code of the prot has been published in https://github.com/loongson-community/musl.  Or check the attachment 0001-port-to-loongarch64.patch, it is the transplanted patch file.
&gt; &gt;
&gt; &gt; Introduction to loongarch architecture:
&gt; &gt; The Loongarch architecture is a simplified instruction computer style instruction system architecture. The instruction length is fixed and the encoding format is regular. Most instructions have only two source operands and one destination operand. The load/store architecture is adopted, that is, only load/store memory access instructions can access the memory, and the operation objects of other instructions are all It is the immediate value in the register or instruction code in the processor core.
&gt; &gt; The Loongson architecture is divided into two versions, 32bit and 64bit, called LA32 and LA64 respectively. LA64 architecture application level is downward binary compatible with LA32 architecture.
&gt; 
&gt; To confirm, Loongarch is basically a fork of MIPS, right?  At least 
&gt; everything seems quite similar in that regard from the patch.  Do you have 
&gt; a simulator available for testing with?
&gt; 
&gt; Ariadne
</chenguoqi@loongson.cn></ariadne@dereferenced.org>

^ permalink raw reply	[flat|nested] 14+ messages in thread

* Re: Re: [musl] Port the new architecture loongarch64 to musl
  2021-05-08  5:23   ` 翟小娟
@ 2021-05-08  7:49     ` Ariadne Conill
  2021-05-12  9:30       ` 翟小娟
  0 siblings, 1 reply; 14+ messages in thread
From: Ariadne Conill @ 2021-05-08  7:49 UTC (permalink / raw)
  To: musl; +Cc: 陈国祺

[-- Attachment #1: Type: text/plain, Size: 385 bytes --]

Hello,

On Sat, 8 May 2021, 翟小娟 wrote:

> Yes, we refer to mips. 
> qemu plans to submit to the community in the near future. For testing and verification, we can provide physical machines or qemu.

The qemu patch would be nice to see, for adaptation of libucontext and 
other things like that.  I can handle libucontext myself if there is a 
working qemu and toolchain.

Ariadne

^ permalink raw reply	[flat|nested] 14+ messages in thread

* Re: Re: [musl] Port the new architecture loongarch64 to musl
  2021-05-08  5:16   ` 翟小娟
@ 2021-05-09  7:56     ` Arnd Bergmann
  0 siblings, 0 replies; 14+ messages in thread
From: Arnd Bergmann @ 2021-05-09  7:56 UTC (permalink / raw)
  To: musl; +Cc: 陈国祺

On Sat, May 8, 2021 at 7:16 AM 翟小娟 <zhaixiaojuan@loongson.cn> wrote:
>
> Yes, we are still using faccessat on the kernel. After the kernel is updated later, we will eliminate these system calls in the musl source code.
> We have already adapted the tool chain, libc, kernel and qemu source code. To ensure quality, we are currently undergoing further testing and
> verification. We plan to start submitting to the community next month. If necessary, we can provide a physical machine or qemu.

I can clarify what is required for merging the kernel port from my perspective:

- In order to review the kernel port on the mailing list, it needs to
be based on the latest release, and split up into
  multiple patches that provide a logical grouping.

- For the initial review, no toolchain, hardware or emulator support is needed.

- When merging the kernel, any review comments have to be addressed,
either by modifying the code, or by
  concluding that your original version was correct.

- Before the kernel is merged, I would expect at the minimum a
confirmation from the toolchain maintainers that
  the compiler can be fully merged into their following release. If
you have a patch against gcc-11 and recent
  binutils,  I can create cross-compiler binaries to build kernels and
host them along with the release builds at
  https://mirrors.edge.kernel.org/pub/tools/crosstool/.

- Validation is *not* a requirement before sending code for review,
and I would consider it a waste of your time,
  since the review tends to find issues that require invasive changes.
I expect that validation is part of your
  process for shipping software to your users, but the part I care
about for mainline support is that the source
  is maintainable in a way that lets others address problems they find.

- qemu support is definitely appreciated, but not a requirement. I'm
personally not planning to run your
   kernels in qemu as part of the review, but others might want to add
loongarch qemu to their automated
   test farms.

If you have a working kernel source tree that you need to rebase
before sending it for review,
I can offer you to take an initial look off-list to point out issues
you should address during the
rebase.

        Arnd

^ permalink raw reply	[flat|nested] 14+ messages in thread

* Re: Re: Re: [musl] Port the new architecture loongarch64 to musl
  2021-05-08  7:49     ` Ariadne Conill
@ 2021-05-12  9:30       ` 翟小娟
  2021-05-12 12:07         ` 罗勇刚(Yonggang Luo)
  2021-05-12 19:53         ` Ariadne Conill
  0 siblings, 2 replies; 14+ messages in thread
From: 翟小娟 @ 2021-05-12  9:30 UTC (permalink / raw)
  To: musl; +Cc: 陈国祺

Hi,
We have ported the code of libucontext for loongarch64 architecture and can be obtained from https://github.com/loongson-community/libucontext 
Currently qemu is still being tested, I will announce it as soon as it is completed.

Xiaojuan Zhai

&gt; -----原始邮件-----
&gt; 发件人: "Ariadne Conill" <ariadne@dereferenced.org>
&gt; 发送时间: 2021-05-08 15:49:50 (星期六)
&gt; 收件人: musl@lists.openwall.com
&gt; 抄送: "陈国祺" <chenguoqi@loongson.cn>
&gt; 主题: Re: Re: [musl] Port the new architecture loongarch64 to musl
&gt; 
&gt; Hello,
&gt; 
&gt; On Sat, 8 May 2021, 翟小娟 wrote:
&gt; 
&gt; &gt; Yes, we refer to mips. 
&gt; &gt; qemu plans to submit to the community in the near future. For testing and verification, we can provide physical machines or qemu.
&gt; 
&gt; The qemu patch would be nice to see, for adaptation of libucontext and 
&gt; other things like that.  I can handle libucontext myself if there is a 
&gt; working qemu and toolchain.
&gt; 
&gt; Ariadne
</chenguoqi@loongson.cn></ariadne@dereferenced.org>

^ permalink raw reply	[flat|nested] 14+ messages in thread

* Re: Re: Re: [musl] Port the new architecture loongarch64 to musl
  2021-05-12  9:30       ` 翟小娟
@ 2021-05-12 12:07         ` 罗勇刚(Yonggang Luo)
  2021-05-12 19:53         ` Ariadne Conill
  1 sibling, 0 replies; 14+ messages in thread
From: 罗勇刚(Yonggang Luo) @ 2021-05-12 12:07 UTC (permalink / raw)
  To: Musl; +Cc: 陈国祺

[-- Attachment #1: Type: text/plain, Size: 1431 bytes --]

Great, I'd like to have a try with loongarch64 architecture.
It's a neat, if possible, please reply the message in plain text format.

On Wed, May 12, 2021 at 5:30 PM 翟小娟 <zhaixiaojuan@loongson.cn> wrote:
>
> Hi,
> We have ported the code of libucontext for loongarch64 architecture and
can be obtained from https://github.com/loongson-community/libucontext
> Currently qemu is still being tested, I will announce it as soon as it is
completed.
>
> Xiaojuan Zhai
>
> &gt; -----原始邮件-----
> &gt; 发件人: "Ariadne Conill" <ariadne@dereferenced.org>
> &gt; 发送时间: 2021-05-08 15:49:50 (星期六)
> &gt; 收件人: musl@lists.openwall.com
> &gt; 抄送: "陈国祺" <chenguoqi@loongson.cn>
> &gt; 主题: Re: Re: [musl] Port the new architecture loongarch64 to musl
> &gt;
> &gt; Hello,
> &gt;
> &gt; On Sat, 8 May 2021, 翟小娟 wrote:
> &gt;
> &gt; &gt; Yes, we refer to mips.
> &gt; &gt; qemu plans to submit to the community in the near future. For
testing and verification, we can provide physical machines or qemu.
> &gt;
> &gt; The qemu patch would be nice to see, for adaptation of libucontext
and
> &gt; other things like that.  I can handle libucontext myself if there is
a
> &gt; working qemu and toolchain.
> &gt;
> &gt; Ariadne
> </chenguoqi@loongson.cn></ariadne@dereferenced.org>



--
         此致
礼
罗勇刚
Yours
    sincerely,
Yonggang Luo

[-- Attachment #2: Type: text/html, Size: 2126 bytes --]

^ permalink raw reply	[flat|nested] 14+ messages in thread

* Re: Re: Re: [musl] Port the new architecture loongarch64 to musl
  2021-05-12  9:30       ` 翟小娟
  2021-05-12 12:07         ` 罗勇刚(Yonggang Luo)
@ 2021-05-12 19:53         ` Ariadne Conill
  2021-05-17 11:19           ` 翟小娟
  1 sibling, 1 reply; 14+ messages in thread
From: Ariadne Conill @ 2021-05-12 19:53 UTC (permalink / raw)
  To: musl; +Cc: 陈国祺

[-- Attachment #1: Type: text/plain, Size: 598 bytes --]

Hi,

On Wed, 12 May 2021, 翟小娟 wrote:

> Hi,
> We have ported the code of libucontext for loongarch64 architecture and can be obtained from https://github.com/loongson-community/libucontext 
> Currently qemu is still being tested, I will announce it as soon as it is completed.

It looks alright, but I am wondering why makecontext is written in 
assembly.  The reason why it is written in assembly for mips had to do 
with specific peculariaties of how the MIPS64 ABI interacted with 
libucontext.  I don't see that the loongarch64 code is trying to capture 
the $gp register though.

Ariadne

^ permalink raw reply	[flat|nested] 14+ messages in thread

* Re: Re: Re: Re: [musl] Port the new architecture loongarch64 to musl
  2021-05-12 19:53         ` Ariadne Conill
@ 2021-05-17 11:19           ` 翟小娟
  0 siblings, 0 replies; 14+ messages in thread
From: 翟小娟 @ 2021-05-17 11:19 UTC (permalink / raw)
  To: musl; +Cc: 陈国祺

The reason for the implementation in assembly  is because I am familiar with assembly myself. I think this shows the implementation logic and final purpose of the function more  clearly than the implementation in C language.


&gt; -----原始邮件-----
&gt; 发件人: "Ariadne Conill" <ariadne@dereferenced.org>
&gt; 发送时间: 2021-05-13 03:53:01 (星期四)
&gt; 收件人: musl@lists.openwall.com
&gt; 抄送: "陈国祺" <chenguoqi@loongson.cn>
&gt; 主题: Re: Re: Re: [musl] Port the new architecture loongarch64 to musl
&gt; 
&gt; Hi,
&gt; 
&gt; On Wed, 12 May 2021, 翟小娟 wrote:
&gt; 
&gt; &gt; Hi,
&gt; &gt; We have ported the code of libucontext for loongarch64 architecture and can be obtained from https://github.com/loongson-community/libucontext 
&gt; &gt; Currently qemu is still being tested, I will announce it as soon as it is completed.
&gt; 
&gt; It looks alright, but I am wondering why makecontext is written in 
&gt; assembly.  The reason why it is written in assembly for mips had to do 
&gt; with specific peculariaties of how the MIPS64 ABI interacted with 
&gt; libucontext.  I don't see that the loongarch64 code is trying to capture 
&gt; the $gp register though.
&gt; 
&gt; Ariadne


</chenguoqi@loongson.cn></ariadne@dereferenced.org>

^ permalink raw reply	[flat|nested] 14+ messages in thread

* Re: Re: [musl] Port the new architecture loongarch64 to musl
       [not found] ` <CAE2XoE_9sQrizuiy0afA1dQdPxgOkPda_39oB9DOJN1c2FB0Cw@mail.gmail.com>
  2021-05-08  5:18   ` 翟小娟
@ 2021-06-24 11:43   ` 翟小娟
  2021-06-24 11:56     ` 罗勇刚(Yonggang Luo)
  1 sibling, 1 reply; 14+ messages in thread
From: 翟小娟 @ 2021-06-24 11:43 UTC (permalink / raw)
  To: musl

[-- Attachment #1: Type: text/plain, Size: 2125 bytes --]

Hi, qemu supports loongarch64 architecture has been completed: https://github.com/loongson/qemu .
For musl loongarch64 source code can also be obtained from https://github.com/loongson-community/musl. If necessary, we can also provide a remote testing enviroment.
See the attachment for specific modifications.

-----原始邮件-----
发件人:"罗勇刚(Yonggang Luo)" <luoyonggang@gmail.com>
发送时间:2021-05-08 00:29:40 (星期六)
收件人: Musl <musl@lists.openwall.com>
抄送: "陈国祺" <chenguoqi@loongson.cn>
主题: Re: [musl] Port the new architecture loongarch64 to musl

Same question, does qemu have already support for  loongarch64, that's means a lot for auto testing
As the real hardware will be not broadly  available in the next few years.  



On Fri, May 7, 2021 at 5:01 PM 翟小娟 <zhaixiaojuan@loongson.cn> wrote:
Hi,
I ported a new architecture loongarch64 on the latest branch of musl master. It has been successfully compiled and run the official test libraries libc-testsuit and libc-test of musl.
The source code of the prot has been published in https://github.com/loongson-community/musl.  Or check the attachment 0001-port-to-loongarch64.patch, it is the transplanted patch file.

Introduction to loongarch architecture:
The Loongarch architecture is a simplified instruction computer style instruction system architecture. The instruction length is fixed and the encoding format is regular. Most instructions have only two source operands and one destination operand. The load/store architecture is adopted, that is, only load/store memory access instructions can access the memory, and the operation objects of other instructions are all It is the immediate value in the register or instruction code in the processor core.
The Loongson architecture is divided into two versions, 32bit and 64bit, called LA32 and LA64 respectively. LA64 architecture application level is downward binary compatible with LA32 architecture.



-- 
此致
礼
罗勇刚
Yours
sincerely,
Yonggang Luo


</zhaixiaojuan@loongson.cn></chenguoqi@loongson.cn></musl@lists.openwall.com></luoyonggang@gmail.com>

[-- Warning: decoded text below may be mangled, UTF-8 assumed --]
[-- Attachment #2: 0001-port-to-loongarch64.patch --]
[-- Type: text/x-patch; name=0001-port-to-loongarch64.patch, Size: 53991 bytes --]

From 137506d1039e0800c6c2631df16f1584c0f64b07 Mon Sep 17 00:00:00 2001
From: zhaixiaojuan <zhaixiaojuan@loongson.cn>
Date: Fri, 7 May 2021 15:35:11 +0800
Subject: [PATCH] port to loongarch64

Signed-off-by: zhaixiaojuan <zhaixiaojuan@loongson.cn>
---
 arch/loongarch64/atomic_arch.h             |  52 ++++
 arch/loongarch64/bits/alltypes.h.in        |  20 ++
 arch/loongarch64/bits/fcntl.h              |  40 +++
 arch/loongarch64/bits/fenv.h               |  25 ++
 arch/loongarch64/bits/float.h              |  16 ++
 arch/loongarch64/bits/hwcap.h              |  15 ++
 arch/loongarch64/bits/posix.h              |   2 +
 arch/loongarch64/bits/ptrace.h             |   4 +
 arch/loongarch64/bits/reg.h                |  66 +++++
 arch/loongarch64/bits/resource.h           |   5 +
 arch/loongarch64/bits/setjmp.h             |   1 +
 arch/loongarch64/bits/signal.h             | 144 ++++++++++
 arch/loongarch64/bits/stat.h               |  20 ++
 arch/loongarch64/bits/statfs.h             |   6 +
 arch/loongarch64/bits/stdint.h             |  20 ++
 arch/loongarch64/bits/syscall.h.in         | 291 +++++++++++++++++++++
 arch/loongarch64/bits/user.h               |   5 +
 arch/loongarch64/crt_arch.h                |  23 ++
 arch/loongarch64/ksigaction.h              |  13 +
 arch/loongarch64/kstat.h                   |  22 ++
 arch/loongarch64/pthread_arch.h            |  13 +
 arch/loongarch64/reloc.h                   |  43 +++
 arch/loongarch64/syscall_arch.h            | 121 +++++++++
 configure                                  |   1 +
 crt/loongarch64/crti.s                     |  15 ++
 crt/loongarch64/crtn.s                     |  12 +
 include/elf.h                              |  65 +++++
 src/fenv/loongarch64/fenv-sf.c             |   3 +
 src/fenv/loongarch64/fenv.S                |  75 ++++++
 src/ldso/loongarch64/dlsym.s               |  12 +
 src/setjmp/loongarch64/longjmp.S           |  37 +++
 src/setjmp/loongarch64/setjmp.S            |  35 +++
 src/signal/loongarch64/restore.s           |  10 +
 src/signal/loongarch64/sigsetjmp.s         |  33 +++
 src/thread/loongarch64/__set_thread_area.s |   7 +
 src/thread/loongarch64/__unmapself.s       |   8 +
 src/thread/loongarch64/clone.s             |  27 ++
 src/thread/loongarch64/syscall_cp.s        |  34 +++
 src/unistd/loongarch64/pipe.s              |  12 +
 39 files changed, 1353 insertions(+)
 create mode 100644 arch/loongarch64/atomic_arch.h
 create mode 100644 arch/loongarch64/bits/alltypes.h.in
 create mode 100644 arch/loongarch64/bits/fcntl.h
 create mode 100644 arch/loongarch64/bits/fenv.h
 create mode 100644 arch/loongarch64/bits/float.h
 create mode 100644 arch/loongarch64/bits/hwcap.h
 create mode 100644 arch/loongarch64/bits/posix.h
 create mode 100644 arch/loongarch64/bits/ptrace.h
 create mode 100644 arch/loongarch64/bits/reg.h
 create mode 100644 arch/loongarch64/bits/resource.h
 create mode 100644 arch/loongarch64/bits/setjmp.h
 create mode 100644 arch/loongarch64/bits/signal.h
 create mode 100644 arch/loongarch64/bits/stat.h
 create mode 100644 arch/loongarch64/bits/statfs.h
 create mode 100644 arch/loongarch64/bits/stdint.h
 create mode 100644 arch/loongarch64/bits/syscall.h.in
 create mode 100644 arch/loongarch64/bits/user.h
 create mode 100644 arch/loongarch64/crt_arch.h
 create mode 100644 arch/loongarch64/ksigaction.h
 create mode 100644 arch/loongarch64/kstat.h
 create mode 100644 arch/loongarch64/pthread_arch.h
 create mode 100644 arch/loongarch64/reloc.h
 create mode 100644 arch/loongarch64/syscall_arch.h
 create mode 100644 crt/loongarch64/crti.s
 create mode 100644 crt/loongarch64/crtn.s
 create mode 100644 src/fenv/loongarch64/fenv-sf.c
 create mode 100644 src/fenv/loongarch64/fenv.S
 create mode 100644 src/ldso/loongarch64/dlsym.s
 create mode 100644 src/setjmp/loongarch64/longjmp.S
 create mode 100644 src/setjmp/loongarch64/setjmp.S
 create mode 100644 src/signal/loongarch64/restore.s
 create mode 100644 src/signal/loongarch64/sigsetjmp.s
 create mode 100644 src/thread/loongarch64/__set_thread_area.s
 create mode 100644 src/thread/loongarch64/__unmapself.s
 create mode 100644 src/thread/loongarch64/clone.s
 create mode 100644 src/thread/loongarch64/syscall_cp.s
 create mode 100644 src/unistd/loongarch64/pipe.s

diff --git a/arch/loongarch64/atomic_arch.h b/arch/loongarch64/atomic_arch.h
new file mode 100644
index 00000000..eb2dedda
--- /dev/null
+++ b/arch/loongarch64/atomic_arch.h
@@ -0,0 +1,52 @@
+#define LLSC_M "m"
+
+#define a_ll a_ll
+static inline int a_ll(volatile int *p)
+{
+	int v;
+	__asm__ __volatile__ (
+		"ll.w %0, %1"
+		: "=r"(v) : LLSC_M(*p));
+	return v;
+}
+
+#define a_sc a_sc
+static inline int a_sc(volatile int *p, int v)
+{
+	int r;
+	__asm__ __volatile__ (
+		"sc.w %0, %1"
+		: "=r"(r), "="LLSC_M(*p) : "0"(v) : "memory");
+	return r;
+}
+
+#define a_ll_p a_ll_p
+static inline void *a_ll_p(volatile void *p)
+{
+	void *v;
+	__asm__ __volatile__ (
+		"ll.d %0, %1"
+		: "=r"(v) : LLSC_M(*(void *volatile *)p));
+	return v;
+}
+
+#define a_sc_p a_sc_p
+static inline int a_sc_p(volatile void *p, void *v)
+{
+	long r;
+	__asm__ __volatile__ (
+		"sc.d %0, %1"
+		: "=r"(r), "="LLSC_M(*(void *volatile *)p) : "0"(v) : "memory");
+	return r;
+}
+
+#define a_barrier a_barrier
+static inline void a_barrier()
+{
+	__asm__ __volatile__ ("dbar 0" : : : "memory");
+}
+
+#define a_pre_llsc a_barrier
+#define a_post_llsc a_barrier
+
+#undef LLSC_M
diff --git a/arch/loongarch64/bits/alltypes.h.in b/arch/loongarch64/bits/alltypes.h.in
new file mode 100644
index 00000000..38871b5f
--- /dev/null
+++ b/arch/loongarch64/bits/alltypes.h.in
@@ -0,0 +1,20 @@
+#define _Addr long
+#define _Int64 long
+#define _Reg long
+
+#define __BYTE_ORDER 1234
+#define __LONG_MAX 0x7fffffffffffffffL
+
+TYPEDEF __builtin_va_list va_list;
+TYPEDEF __builtin_va_list __isoc_va_list;
+
+#ifndef __cplusplus
+TYPEDEF int wchar_t;
+#endif
+
+TYPEDEF float float_t;
+TYPEDEF double double_t;
+
+TYPEDEF struct { long long __ll; long double __ld; } max_align_t;
+
+TYPEDEF unsigned nlink_t;
diff --git a/arch/loongarch64/bits/fcntl.h b/arch/loongarch64/bits/fcntl.h
new file mode 100644
index 00000000..9bcbb7ff
--- /dev/null
+++ b/arch/loongarch64/bits/fcntl.h
@@ -0,0 +1,40 @@
+#define O_CREAT        0100
+#define O_EXCL         0200
+#define O_NOCTTY       0400
+#define O_TRUNC       01000
+#define O_APPEND      02000
+#define O_NONBLOCK    04000
+#define O_DSYNC      010000
+#define O_SYNC     04010000
+#define O_RSYNC    04010000
+#define O_DIRECTORY 0200000
+#define O_NOFOLLOW  0400000
+#define O_CLOEXEC  02000000
+
+#define O_ASYNC      020000
+#define O_DIRECT     040000
+#define O_LARGEFILE 0100000
+#define O_NOATIME  01000000
+#define O_PATH    010000000
+#define O_TMPFILE 020000000
+#define O_NDELAY O_NONBLOCK
+
+#define F_DUPFD  0
+#define F_GETFD  1
+#define F_SETFD  2
+#define F_GETFL  3
+#define F_SETFL  4
+
+#define F_SETOWN 8
+#define F_GETOWN 9
+#define F_SETSIG 10
+#define F_GETSIG 11
+
+#define F_GETLK  5
+#define F_SETLK  6
+#define F_SETLKW 7
+
+#define F_SETOWN_EX 15
+#define F_GETOWN_EX 16
+
+#define F_GETOWNER_UIDS 17
diff --git a/arch/loongarch64/bits/fenv.h b/arch/loongarch64/bits/fenv.h
new file mode 100644
index 00000000..6f98053a
--- /dev/null
+++ b/arch/loongarch64/bits/fenv.h
@@ -0,0 +1,25 @@
+#ifdef __loongarch_soft_float
+#define FE_ALL_EXCEPT 0
+#define FE_TONEAREST  0
+#else
+#define FE_INEXACT    0x010000
+#define FE_UNDERFLOW  0x020000
+#define FE_OVERFLOW   0x040000
+#define FE_DIVBYZERO  0x080000
+#define FE_INVALID    0x100000
+
+#define FE_ALL_EXCEPT 0x1F0000
+
+#define FE_TONEAREST  0x000
+#define FE_TOWARDZERO 0x100
+#define FE_UPWARD     0x200
+#define FE_DOWNWARD   0x300
+#endif
+
+typedef unsigned fexcept_t;
+
+typedef struct {
+	unsigned __cw;
+} fenv_t;
+
+#define FE_DFL_ENV ((const fenv_t *) -1)
diff --git a/arch/loongarch64/bits/float.h b/arch/loongarch64/bits/float.h
new file mode 100644
index 00000000..719c7908
--- /dev/null
+++ b/arch/loongarch64/bits/float.h
@@ -0,0 +1,16 @@
+#define FLT_EVAL_METHOD 0
+
+#define LDBL_TRUE_MIN 6.47517511943802511092443895822764655e-4966L
+#define LDBL_MIN 3.36210314311209350626267781732175260e-4932L
+#define LDBL_MAX 1.18973149535723176508575932662800702e+4932L
+#define LDBL_EPSILON 1.92592994438723585305597794258492732e-34L
+
+#define LDBL_MANT_DIG 113
+#define LDBL_MIN_EXP (-16381)
+#define LDBL_MAX_EXP 16384
+
+#define LDBL_DIG 33
+#define LDBL_MIN_10_EXP (-4931)
+#define LDBL_MAX_10_EXP 4932
+
+#define DECIMAL_DIG 36
diff --git a/arch/loongarch64/bits/hwcap.h b/arch/loongarch64/bits/hwcap.h
new file mode 100644
index 00000000..bb505da8
--- /dev/null
+++ b/arch/loongarch64/bits/hwcap.h
@@ -0,0 +1,15 @@
+/* HWCAP - Hardware Capabilities
+ * Hardware information is not clear at present, leave it blank. 
+ */
+#define HWCAP_LOONGARCH_CPUCFG	(1 << 0)
+#define HWCAP_LOONGARCH_FPU	(1 << 1)
+#define HWCAP_LOONGARCH_LSX	(1 << 2)  /* support 128bit vectors*/
+#define HWCAP_LOONGARCH_LASX	(1 << 3)  /* support 256bit vectors*/
+#define HWCAP_LOONGARCH_LBT	(1 << 4)  /* support LBT*/
+#define HWCAP_LOONGARCH_LVZ	(1 << 5)  /* support virtualization expansion*/
+#define HWCAP_LOONGARCH_CRC32	(1 << 7)  /* support CRC32 check*/
+#define HWCAP_LOONGARCH_AES	(1 << 6)
+#define HWCAP_LOONGARCH_SHA1	(1 << 8)
+#define HWCAP_LOONGARCH_SHA2	(1 << 9)
+#define HWCAP_LOONGARCH_SHA3	(1 << 10)
+
diff --git a/arch/loongarch64/bits/posix.h b/arch/loongarch64/bits/posix.h
new file mode 100644
index 00000000..8068ce98
--- /dev/null
+++ b/arch/loongarch64/bits/posix.h
@@ -0,0 +1,2 @@
+#define _POSIX_V6_LP64_OFF64 1
+#define _POSIX_V7_LP64_OFF64 1
diff --git a/arch/loongarch64/bits/ptrace.h b/arch/loongarch64/bits/ptrace.h
new file mode 100644
index 00000000..741fc668
--- /dev/null
+++ b/arch/loongarch64/bits/ptrace.h
@@ -0,0 +1,4 @@
+#define PTRACE_GET_THREAD_AREA	25
+#define PTRACE_SET_THREAD_AREA	26
+#define PTRACE_GET_WATCH_REGS	0xd0
+#define PTRACE_SET_WATCH_REGS	0xd1
diff --git a/arch/loongarch64/bits/reg.h b/arch/loongarch64/bits/reg.h
new file mode 100644
index 00000000..5d3f92c5
--- /dev/null
+++ b/arch/loongarch64/bits/reg.h
@@ -0,0 +1,66 @@
+#undef __WORDSIZE
+#define __WORDSIZE 64
+#define LOONGARCH64_EF_R0   0
+#define LOONGARCH64_EF_R1   1
+#define LOONGARCH64_EF_R2   2
+#define LOONGARCH64_EF_R3   3
+#define LOONGARCH64_EF_R4   4
+#define LOONGARCH64_EF_R5   5
+#define LOONGARCH64_EF_R6   6
+#define LOONGARCH64_EF_R7   7
+#define LOONGARCH64_EF_R8   8
+#define LOONGARCH64_EF_R9   9
+#define LOONGARCH64_EF_R10    10
+#define LOONGARCH64_EF_R11    11
+#define LOONGARCH64_EF_R12    12
+#define LOONGARCH64_EF_R13    13
+#define LOONGARCH64_EF_R14    14
+#define LOONGARCH64_EF_R15    15
+#define LOONGARCH64_EF_R16    16
+#define LOONGARCH64_EF_R17    17
+#define LOONGARCH64_EF_R18    18
+#define LOONGARCH64_EF_R19    19
+#define LOONGARCH64_EF_R20    20
+#define LOONGARCH64_EF_R21    21
+#define LOONGARCH64_EF_R22    22
+#define LOONGARCH64_EF_R23    23
+#define LOONGARCH64_EF_R24    24
+#define LOONGARCH64_EF_R25    25
+#define LOONGARCH64_EF_R26    26
+#define LOONGARCH64_EF_R27    27
+#define LOONGARCH64_EF_R28    28
+#define LOONGARCH64_EF_R29    29
+#define LOONGARCH64_EF_R30    30
+#define LOONGARCH64_EF_R31    31
+
+#define LOONGARCH64_EF_SIZE   304 /* size in bytes */
+
+#define EF_R0     LOONGARCH64_EF_R0
+#define EF_R1     LOONGARCH64_EF_R1
+#define EF_R2     LOONGARCH64_EF_R2
+#define EF_R3     LOONGARCH64_EF_R3
+#define EF_R4     LOONGARCH64_EF_R4
+#define EF_R5     LOONGARCH64_EF_R5
+#define EF_R6     LOONGARCH64_EF_R6
+#define EF_R7     LOONGARCH64_EF_R7
+#define EF_R8     LOONGARCH64_EF_R8
+#define EF_R9     LOONGARCH64_EF_R9
+#define EF_R10      LOONGARCH64_EF_R10
+#define EF_R11      LOONGARCH64_EF_R11
+#define EF_R12      LOONGARCH64_EF_R12
+#define EF_R13      LOONGARCH64_EF_R13
+#define EF_R14      LOONGARCH64_EF_R14
+#define EF_R15      LOONGARCH64_EF_R15
+#define EF_R16      LOONGARCH64_EF_R16
+#define EF_R17      LOONGARCH64_EF_R17
+#define EF_R18      LOONGARCH64_EF_R18
+#define EF_R19      LOONGARCH64_EF_R19
+#define EF_R20      LOONGARCH64_EF_R20
+#define EF_R21      LOONGARCH64_EF_R21
+#define EF_R22      LOONGARCH64_EF_R22
+#define EF_R23      LOONGARCH64_EF_R23
+#define EF_R24      LOONGARCH64_EF_R24
+#define EF_R25      LOONGARCH64_EF_R25
+#define EF_R26      LOONGARCH64_EF_R26
+#define EF_R27      LOONGARCH64_EF_R27
+#define EF_R28      LOONGARCH64_EF_R28
diff --git a/arch/loongarch64/bits/resource.h b/arch/loongarch64/bits/resource.h
new file mode 100644
index 00000000..da983617
--- /dev/null
+++ b/arch/loongarch64/bits/resource.h
@@ -0,0 +1,5 @@
+#define RLIMIT_NOFILE  7 /* num of file limit, able to open file */
+#define RLIMIT_AS      9 /* address space limit */
+#define RLIMIT_RSS     5 /* max resident set size */
+#define RLIMIT_NPROC   6 /* max number of processes */
+#define RLIMIT_MEMLOCK 8 /* max locked-in-memory address space */
diff --git a/arch/loongarch64/bits/setjmp.h b/arch/loongarch64/bits/setjmp.h
new file mode 100644
index 00000000..f4a7f8a3
--- /dev/null
+++ b/arch/loongarch64/bits/setjmp.h
@@ -0,0 +1 @@
+typedef unsigned long long __jmp_buf[22];
diff --git a/arch/loongarch64/bits/signal.h b/arch/loongarch64/bits/signal.h
new file mode 100644
index 00000000..318551a7
--- /dev/null
+++ b/arch/loongarch64/bits/signal.h
@@ -0,0 +1,144 @@
+#if defined(_POSIX_SOURCE) || defined(_POSIX_C_SOURCE) \
+ || defined(_XOPEN_SOURCE) || defined(_GNU_SOURCE) || defined(_BSD_SOURCE)
+
+#if defined(_XOPEN_SOURCE) || defined(_GNU_SOURCE) || defined(_BSD_SOURCE)
+#define MINSIGSTKSZ 8192
+#define SIGSTKSZ (MINSIGSTKSZ + 32768)
+#endif
+
+#define ARCH_MIN_TASKALIGN	32
+#define FPU_REG_WIDTH		256
+#define FPU_ALIGN		__attribute__((aligned(32)))
+
+#if defined(_GNU_SOURCE) || defined(_BSD_SOURCE)
+typedef unsigned long greg_t, gregset_t[32];
+
+struct sigcontext {
+	unsigned long   sc_pc;
+	unsigned long   sc_regs[32];
+	unsigned int    sc_flags;
+	unsigned int    sc_fcsr;
+	unsigned int    sc_vcsr;
+	unsigned long   sc_fcc;
+	unsigned long   sc_scr[4];
+	union {
+		unsigned int		val32[FPU_REG_WIDTH / 32];
+		unsigned long long	val64[FPU_REG_WIDTH / 64];
+	} sc_fpregs[32] FPU_ALIGN;
+	unsigned char	sc_reserved[4096] __attribute__((__aligned__(16)));
+};
+
+typedef struct {
+	unsigned long   pc;
+	unsigned long   gregs[32];
+	unsigned int    flags;
+	unsigned int    fcsr;
+	unsigned int    vcsr;
+	unsigned long   fcc;
+	unsigned long   scr[4];
+	union {
+                unsigned int            val32[FPU_REG_WIDTH / 32];
+                unsigned long long      val64[FPU_REG_WIDTH / 64];
+        } fpregs[32] FPU_ALIGN;
+	unsigned char   reserved[4096] __attribute__((__aligned__(16)));
+} mcontext_t;
+
+#else
+typedef struct {
+	unsigned long __mc1[32];
+	union {
+                unsigned int            val32[FPU_REG_WIDTH / 32];
+                unsigned long long      val64[FPU_REG_WIDTH / 64];
+        } _mc2[32] FPU_ALIGN;
+	unsigned int __mc3[3];
+	unsigned long __mc4[2];
+	unsigned long __mc5[4];
+	unsigned char reserved[4096] __attribute__((__aligned__(16)));
+} mcontext_t;
+
+#endif
+
+struct sigaltstack {
+	void *ss_sp;
+	int ss_flags;
+	size_t ss_size;
+};
+
+typedef struct __ucontext
+{
+	unsigned long  __uc_flags;
+	struct __ucontext *uc_link;
+	stack_t            uc_stack;
+	mcontext_t uc_mcontext;
+	sigset_t           uc_sigmask;
+} ucontext_t;
+
+
+#define SA_NOCLDSTOP  1          /* Don't send SIGCHLD when children stop.  */
+#define SA_NOCLDWAIT  2          /* Don't create zombie on child death.  */
+#define SA_SIGINFO    4          /* Invoke signal-catching function with
+                                    three arguments instead of one.  */
+#define SA_ONSTACK   0x08000000 /* Use signal stack by using `sa_restorer'. */
+#define SA_RESTART   0x10000000 /* Restart syscall on signal return.  */
+#define SA_NODEFER   0x40000000 /* Don't automatically block the signal when
+                                    its handler is being executed.  */
+#define SA_RESETHAND 0x80000000 /* Reset to SIG_DFL on entry to handler.  */
+#define SA_RESTORER  0x04000000
+
+#undef SIG_BLOCK
+#undef SIG_UNBLOCK
+#undef SIG_SETMASK
+#define SIG_BLOCK     0
+#define SIG_UNBLOCK   1
+#define SIG_SETMASK   2
+
+#undef SI_ASYNCIO
+#undef SI_MESGQ
+#undef SI_TIMER
+#define SI_ASYNCIO (-4)
+#define SI_MESGQ (-3)
+#define SI_TIMER (-2)
+
+
+#endif
+
+#define SIGHUP           1
+#define SIGINT           2
+#define SIGQUIT          3
+#define SIGILL           4
+#define SIGTRAP          5
+#define SIGABRT          6
+#define SIGIOT           6
+#define SIGBUS           7
+#define SIGFPE           8
+#define SIGKILL          9
+#define SIGUSR1         10
+#define SIGSEGV         11
+#define SIGUSR2         12
+#define SIGPIPE         13
+#define SIGALRM         14
+#define SIGTERM         15
+#define SIGSTKFLT       16
+#define SIGCHLD         17
+#define SIGCONT         18
+#define SIGSTOP         19
+#define SIGTSTP         20
+#define SIGTTIN         21
+#define SIGTTOU         22
+#define SIGURG          23
+#define SIGXCPU         24
+#define SIGXFSZ         25
+#define SIGVTALRM       26
+#define SIGPROF         27
+#define SIGWINCH        28
+#define SIGIO           29
+#define SIGPOLL         SIGIO
+/*
+#define SIGLOST         29
+*/
+#define SIGPWR          30
+#define SIGSYS          31
+
+#define SIGUNUSED SIGSYS
+
+#define _NSIG 128
diff --git a/arch/loongarch64/bits/stat.h b/arch/loongarch64/bits/stat.h
new file mode 100644
index 00000000..b620e142
--- /dev/null
+++ b/arch/loongarch64/bits/stat.h
@@ -0,0 +1,20 @@
+struct stat {
+	dev_t st_dev;
+	int __pad1[3];
+	ino_t st_ino;
+	mode_t st_mode;
+	nlink_t st_nlink;
+	uid_t st_uid;
+	gid_t st_gid;
+	dev_t st_rdev;
+	unsigned int __pad2[2];
+	off_t st_size;
+	int __pad3;
+	struct timespec st_atim;
+	struct timespec st_mtim;
+	struct timespec st_ctim;
+	blksize_t st_blksize;
+	unsigned int __pad4;
+	blkcnt_t st_blocks;
+	int __pad5[14];
+};
diff --git a/arch/loongarch64/bits/statfs.h b/arch/loongarch64/bits/statfs.h
new file mode 100644
index 00000000..389954ae
--- /dev/null
+++ b/arch/loongarch64/bits/statfs.h
@@ -0,0 +1,6 @@
+struct statfs {
+	long f_type, f_bsize;
+	unsigned long f_blocks, f_bfree, f_bavail, f_files, f_ffree;
+	fsid_t f_fsid;
+	long f_namelen, f_frsize, f_flags, f_spare[4];
+};
diff --git a/arch/loongarch64/bits/stdint.h b/arch/loongarch64/bits/stdint.h
new file mode 100644
index 00000000..1bb147f2
--- /dev/null
+++ b/arch/loongarch64/bits/stdint.h
@@ -0,0 +1,20 @@
+typedef int32_t int_fast16_t;
+typedef int32_t int_fast32_t;
+typedef uint32_t uint_fast16_t;
+typedef uint32_t uint_fast32_t;
+
+#define INT_FAST16_MIN  INT32_MIN
+#define INT_FAST32_MIN  INT32_MIN
+
+#define INT_FAST16_MAX  INT32_MAX
+#define INT_FAST32_MAX  INT32_MAX
+
+#define UINT_FAST16_MAX UINT32_MAX
+#define UINT_FAST32_MAX UINT32_MAX
+
+#define INTPTR_MIN      INT64_MIN
+#define INTPTR_MAX      INT64_MAX
+#define UINTPTR_MAX     UINT64_MAX
+#define PTRDIFF_MIN     INT64_MIN
+#define PTRDIFF_MAX     INT64_MAX
+#define SIZE_MAX        UINT64_MAX
diff --git a/arch/loongarch64/bits/syscall.h.in b/arch/loongarch64/bits/syscall.h.in
new file mode 100644
index 00000000..74bfd799
--- /dev/null
+++ b/arch/loongarch64/bits/syscall.h.in
@@ -0,0 +1,291 @@
+#define __NR_io_setup                   0
+#define __NR_io_destroy                 1
+#define __NR_io_submit                  2
+#define __NR_io_cancel                  3
+#define __NR_io_getevents               4
+#define __NR_setxattr                   5
+#define __NR_lsetxattr                  6
+#define __NR_fsetxattr                  7
+#define __NR_getxattr                   8
+#define __NR_lgetxattr                  9
+#define __NR_fgetxattr                  10
+#define __NR_listxattr                  11
+#define __NR_llistxattr                 12
+#define __NR_flistxattr                 13
+#define __NR_removexattr                14
+#define __NR_lremovexattr               15
+#define __NR_fremovexattr               16
+#define __NR_getcwd                     17
+#define __NR_lookup_dcookie             18
+#define __NR_eventfd2                   19
+#define __NR_epoll_create1              20
+#define __NR_epoll_ctl                  21
+#define __NR_epoll_pwait                22
+#define __NR_dup                        23
+#define __NR_dup3                       24
+#define __NR3264_fcntl                  25
+#define __NR_inotify_init1              26
+#define __NR_inotify_add_watch          27
+#define __NR_inotify_rm_watch           28
+#define __NR_ioctl                      29
+#define __NR_ioprio_set                 30
+#define __NR_ioprio_get                 31
+#define __NR_flock                      32
+#define __NR_mknodat                    33
+#define __NR_mkdirat                    34
+#define __NR_unlinkat                   35
+#define __NR_symlinkat                  36
+#define __NR_linkat                     37
+#define __NR_umount2                    39
+#define __NR_mount                      40
+#define __NR_pivot_root                 41
+#define __NR_nfsservctl                 42
+#define __NR3264_statfs                 43
+#define __NR3264_fstatfs                44
+#define __NR3264_truncate               45
+#define __NR3264_ftruncate              46
+#define __NR_fallocate                  47
+#define __NR_faccessat                  48
+#define __NR_faccessat2                 48
+#define __NR_chdir                      49
+#define __NR_fchdir                     50
+#define __NR_chroot                     51
+#define __NR_fchmod                     52
+#define __NR_fchmodat                   53
+#define __NR_fchownat                   54
+#define __NR_fchown                     55
+#define __NR_openat                     56
+#define __NR_close                      57
+#define __NR_vhangup                    58
+#define __NR_pipe2                      59
+#define __NR_quotactl                   60
+#define __NR_getdents64                 61
+#define __NR3264_lseek                  62
+#define __NR_read                       63
+#define __NR_write                      64
+#define __NR_readv                      65
+#define __NR_writev                     66
+#define __NR_pread64                    67
+#define __NR_pwrite64                   68
+#define __NR_preadv                     69
+#define __NR_pwritev                    70
+#define __NR3264_sendfile               71
+#define __NR_pselect6                   72
+#define __NR_ppoll                      73
+#define __NR_signalfd4                  74
+#define __NR_vmsplice                   75
+#define __NR_splice                     76
+#define __NR_tee                        77
+#define __NR_readlinkat                 78
+#define __NR3264_fstatat                79
+#define __NR3264_fstat                  80
+#define __NR_sync                       81
+#define __NR_fsync                      82
+#define __NR_fdatasync                  83
+#define __NR_sync_file_range            84
+#define __NR_timerfd_create             85
+#define __NR_timerfd_settime            86
+#define __NR_timerfd_gettime            87
+#define __NR_utimensat                  88
+#define __NR_acct                       89
+#define __NR_capget                     90
+#define __NR_capset                     91
+#define __NR_personality                92
+#define __NR_exit                       93
+#define __NR_exit_group                 94
+#define __NR_waitid                     95
+#define __NR_set_tid_address            96
+#define __NR_unshare                    97
+#define __NR_futex                      98
+#define __NR_set_robust_list            99
+#define __NR_get_robust_list            100
+#define __NR_nanosleep                  101
+#define __NR_getitimer                  102
+#define __NR_setitimer                  103
+#define __NR_kexec_load                 104
+#define __NR_init_module                105
+#define __NR_delete_module              106
+#define __NR_timer_create               107
+#define __NR_timer_gettime              108
+#define __NR_timer_getoverrun           109
+#define __NR_timer_settime              110
+#define __NR_timer_delete               111
+#define __NR_clock_settime              112
+#define __NR_clock_gettime              113
+#define __NR_clock_getres               114
+#define __NR_clock_nanosleep            115
+#define __NR_syslog                     116
+#define __NR_ptrace                     117
+#define __NR_sched_setparam             118
+#define __NR_sched_setscheduler         119
+#define __NR_sched_getscheduler         120
+#define __NR_sched_getparam             121
+#define __NR_sched_setaffinity          122
+#define __NR_sched_getaffinity          123
+#define __NR_sched_yield                124
+#define __NR_sched_get_priority_max     125
+#define __NR_sched_get_priority_min     126
+#define __NR_sched_rr_get_interval      127
+#define __NR_restart_syscall            128
+#define __NR_kill                       129
+#define __NR_tkill                      130
+#define __NR_tgkill                     131
+#define __NR_sigaltstack                132
+#define __NR_rt_sigsuspend              133
+#define __NR_rt_sigaction               134
+#define __NR_rt_sigprocmask             135
+#define __NR_rt_sigpending              136
+#define __NR_rt_sigtimedwait            137
+#define __NR_rt_sigqueueinfo            138
+#define __NR_rt_sigreturn               139
+#define __NR_setpriority                140
+#define __NR_getpriority                141
+#define __NR_reboot                     142
+#define __NR_setregid                   143
+#define __NR_setgid                     144
+#define __NR_setreuid                   145
+#define __NR_setuid                     146
+#define __NR_setresuid                  147
+#define __NR_getresuid                  148
+#define __NR_setresgid                  149
+#define __NR_getresgid                  150
+#define __NR_setfsuid                   151
+#define __NR_setfsgid                   152
+#define __NR_times                      153
+#define __NR_setpgid                    154
+#define __NR_getpgid                    155
+#define __NR_getsid                     156
+#define __NR_setsid                     157
+#define __NR_getgroups                  158
+#define __NR_setgroups                  159
+#define __NR_uname                      160
+#define __NR_sethostname                161
+#define __NR_setdomainname              162
+#define __NR_getrlimit                  163
+#define __NR_setrlimit                  164
+#define __NR_getrusage                  165
+#define __NR_umask                      166
+#define __NR_prctl                      167
+#define __NR_getcpu                     168
+#define __NR_gettimeofday               169
+#define __NR_settimeofday               170
+#define __NR_adjtimex                   171
+#define __NR_getpid                     172
+#define __NR_getppid                    173
+#define __NR_getuid                     174
+#define __NR_geteuid                    175
+#define __NR_getgid                     176
+#define __NR_getegid                    177
+#define __NR_gettid                     178
+#define __NR_sysinfo                    179
+#define __NR_mq_open                    180
+#define __NR_mq_unlink                  181
+#define __NR_mq_timedsend               182
+#define __NR_mq_timedreceive            183
+#define __NR_mq_notify                  184
+#define __NR_mq_getsetattr              185
+#define __NR_msgget                     186
+#define __NR_msgctl                     187
+#define __NR_msgrcv                     188
+#define __NR_msgsnd                     189
+#define __NR_semget                     190
+#define __NR_semctl                     191
+#define __NR_semtimedop                 192
+#define __NR_semop                      193
+#define __NR_shmget                     194
+#define __NR_shmctl                     195
+#define __NR_shmat                      196
+#define __NR_shmdt                      197
+#define __NR_socket                     198
+#define __NR_socketpair                 199
+#define __NR_bind                       200
+#define __NR_listen                     201
+#define __NR_accept                     202
+#define __NR_connect                    203
+#define __NR_getsockname                204
+#define __NR_getpeername                205
+#define __NR_sendto                     206
+#define __NR_recvfrom                   207
+#define __NR_setsockopt                 208
+#define __NR_getsockopt                 209
+#define __NR_shutdown                   210
+#define __NR_sendmsg                    211
+#define __NR_recvmsg                    212
+#define __NR_readahead                  213
+#define __NR_brk                        214
+#define __NR_munmap                     215
+#define __NR_mremap                     216
+#define __NR_add_key                    217
+#define __NR_request_key                218
+#define __NR_keyctl                     219
+#define __NR_clone                      220
+#define __NR_execve                     221
+#define __NR3264_mmap                   222
+#define __NR3264_fadvise64              223
+#define __NR_swapon                     224
+#define __NR_swapoff                    225
+#define __NR_mprotect                   226
+#define __NR_msync                      227
+#define __NR_mlock                      228
+#define __NR_munlock                    229
+#define __NR_mlockall                   230
+#define __NR_munlockall                 231
+#define __NR_mincore                    232
+#define __NR_madvise                    233
+#define __NR_remap_file_pages           234
+#define __NR_mbind                      235
+#define __NR_get_mempolicy              236
+#define __NR_set_mempolicy              237
+#define __NR_migrate_pages              238
+#define __NR_move_pages                 239
+#define __NR_rt_tgsigqueueinfo          240
+#define __NR_perf_event_open            241
+#define __NR_accept4                    242
+#define __NR_recvmmsg                   243
+#define __NR_arch_specific_syscall      244
+#define __NR_wait4                      260
+#define __NR_prlimit64                  261
+#define __NR_fanotify_init              262
+#define __NR_fanotify_mark              263
+#define __NR_name_to_handle_at          264
+#define __NR_open_by_handle_at          265
+#define __NR_clock_adjtime              266
+#define __NR_syncfs                     267
+#define __NR_setns                      268
+#define __NR_sendmmsg                   269
+#define __NR_process_vm_readv           270
+#define __NR_process_vm_writev          271
+#define __NR_kcmp                       272
+#define __NR_finit_module               273
+#define __NR_sched_setattr              274
+#define __NR_sched_getattr              275
+#define __NR_renameat2                  276
+#define __NR_seccomp                    277
+#define __NR_getrandom                  278
+#define __NR_memfd_create               279
+#define __NR_bpf                        280
+#define __NR_execveat                   281
+#define __NR_userfaultfd                282
+#define __NR_membarrier                 283
+#define __NR_mlock2                     284
+#define __NR_copy_file_range            285
+#define __NR_preadv2                    286
+#define __NR_pwritev2                   287
+#define __NR_pkey_mprotect              288
+#define __NR_pkey_alloc                 289
+#define __NR_pkey_free                  290
+#define __NR_statx                      291
+#define __NR_io_pgetevents              292
+#define __NR_rseq                       293
+#define __NR_syscalls                   294
+#define __NR_fcntl                      __NR3264_fcntl
+#define __NR_statfs                     __NR3264_statfs
+#define __NR_fstatfs                    __NR3264_fstatfs
+#define __NR_truncate                   __NR3264_truncate
+#define __NR_ftruncate                  __NR3264_ftruncate
+#define __NR_lseek                      __NR3264_lseek
+#define __NR_sendfile                   __NR3264_sendfile
+#define __NR_newfstatat                 __NR3264_fstatat
+#define __NR_fstat                      __NR3264_fstat
+#define __NR_mmap                       __NR3264_mmap
+#define __NR_fadvise64                  __NR3264_fadvise64
diff --git a/arch/loongarch64/bits/user.h b/arch/loongarch64/bits/user.h
new file mode 100644
index 00000000..4d4cd534
--- /dev/null
+++ b/arch/loongarch64/bits/user.h
@@ -0,0 +1,5 @@
+#define ELF_NGREG	45
+#define ELF_NFPREG	33
+
+typedef unsigned long elf_greg_t, elf_gregset_t[ELF_NGREG];
+typedef double elf_fpreg_t, elf_fpregset_t[ELF_NFPREG];
diff --git a/arch/loongarch64/crt_arch.h b/arch/loongarch64/crt_arch.h
new file mode 100644
index 00000000..3db6aad5
--- /dev/null
+++ b/arch/loongarch64/crt_arch.h
@@ -0,0 +1,23 @@
+__asm__(
+".text \n"
+".global _" START "\n"
+".global " START "\n"
+".global " START "_data\n"
+".type   _" START ", @function\n"
+".type   " START ", @function\n"
+".type   " START "_data, @function\n"
+"_" START ":\n"
+"" START ":\n"
+".align 8 \n"
+"	add.w $fp, $r0,$r0 \n"
+"	bl 1f \n"
+"" START "_data: \n"
+".weak _DYNAMIC \n"
+".hidden _DYNAMIC \n"
+"1:	or $a0, $sp, $zero \n"
+"	la.local $a1, _DYNAMIC \n"
+"	addi.w $r19, $r0, -16 \n"
+"	and $sp, $sp, $r19 \n"
+"	la.local $t0," START "_c \n"
+"	jirl $t1,$t0,0 \n"
+);
diff --git a/arch/loongarch64/ksigaction.h b/arch/loongarch64/ksigaction.h
new file mode 100644
index 00000000..0d352e8c
--- /dev/null
+++ b/arch/loongarch64/ksigaction.h
@@ -0,0 +1,13 @@
+#include <features.h>
+
+/* This is the structure used for the rt_sigaction syscall on most archs,
+ * but it can be overridden by a file with the same name in the top-level
+ * arch dir for a given arch, if necessary. */
+struct k_sigaction {
+	void (*handler)(int);
+	unsigned long flags;
+	unsigned long mask[2];
+	void (*restorer)();
+};
+
+hidden void __restore(), __restore_rt();
diff --git a/arch/loongarch64/kstat.h b/arch/loongarch64/kstat.h
new file mode 100644
index 00000000..f66ed2e9
--- /dev/null
+++ b/arch/loongarch64/kstat.h
@@ -0,0 +1,22 @@
+struct kstat {
+    unsigned long   st_dev;     /* Device.  */
+    unsigned long   st_ino;     /* File serial number.  */
+    unsigned int    st_mode;    /* File mode.  */
+    unsigned int    st_nlink;   /* Link count.  */
+    unsigned int    st_uid;     /* User ID of the file's owner.  */
+    unsigned int    st_gid;     /* Group ID of the file's group. */
+    unsigned long   st_rdev;    /* Device number, if device.  */
+    unsigned long   __pad1;
+    long        st_size;    /* Size of file, in bytes.  */
+    int     st_blksize; /* Optimal block size for I/O.  */
+    int     __pad2;
+    long        st_blocks;  /* Number 512-byte blocks allocated. */
+    long        st_atime_sec;   /* Time of last access.  */
+    unsigned long   st_atime_nsec;
+    long        st_mtime_sec;   /* Time of last modification.  */
+    unsigned long   st_mtime_nsec;
+    long        st_ctime_sec;   /* Time of last status change.  */
+    unsigned long   st_ctime_nsec;
+    unsigned int    __unused4;
+    unsigned int    __unused5;
+};
diff --git a/arch/loongarch64/pthread_arch.h b/arch/loongarch64/pthread_arch.h
new file mode 100644
index 00000000..27f50e4c
--- /dev/null
+++ b/arch/loongarch64/pthread_arch.h
@@ -0,0 +1,13 @@
+static inline uintptr_t __get_tp()
+{
+	uintptr_t tp;
+	__asm__ ("or %0, $tp, $zero" : "=r" (tp) );
+	return tp;
+}
+
+#define TLS_ABOVE_TP
+#define GAP_ABOVE_TP 0
+
+#define DTP_OFFSET 0
+
+#define MC_PC pc
diff --git a/arch/loongarch64/reloc.h b/arch/loongarch64/reloc.h
new file mode 100644
index 00000000..6e2b67e9
--- /dev/null
+++ b/arch/loongarch64/reloc.h
@@ -0,0 +1,43 @@
+#ifndef __RELOC_H__
+#define __RELOC_H__
+
+#define _GNU_SOURCE
+#include <endian.h>
+
+#ifdef __loongarch64_soft_float
+#define FP_SUFFIX "-sf"
+#else
+#define FP_SUFFIX ""
+#endif
+
+#define LDSO_ARCH "loongarch64"  FP_SUFFIX
+
+#define TPOFF_K (0x0)
+
+//#define REL_SYM_OR_REL  4611  
+#define REL_PLT         R_LOONGARCH_JUMP_SLOT
+#define REL_COPY        R_LOONGARCH_COPY
+#define REL_DTPMOD      R_LOONGARCH_TLS_DTPMOD64
+#define REL_DTPOFF      R_LOONGARCH_TLS_DTPREL64
+#define REL_TPOFF       R_LOONGARCH_TLS_TPREL64
+#define REL_RELATIVE    R_LOONGARCH_RELATIVE
+#define REL_SYMBOLIC    R_LOONGARCH_64
+
+//#undef R_TYPE
+//#undef R_SYM
+//#undef R_INFO
+//#define R_TYPE(x) (be64toh(x)&0x7fffffff)
+//#define R_SYM(x) (be32toh(be64toh(x)>>32))
+//#define R_INFO(s,t) (htobe64((uint64_t)htobe32(s)<<32 | (uint64_t)t))
+
+#define CRTJMP(pc,sp) __asm__ __volatile__( \
+	"move $sp,%1 ; jr %0" : : "r"(pc), "r"(sp) : "memory" )
+
+#define GETFUNCSYM(fp, sym, got) __asm__ ( \
+	".hidden " #sym "\n" \
+	".align 8 \n" \
+	"	la.local $t1, "#sym" \n" \
+	"	or %0, $t1, $zero \n" \
+	: "=r"(*(fp)) : : "memory" )
+
+#endif
diff --git a/arch/loongarch64/syscall_arch.h b/arch/loongarch64/syscall_arch.h
new file mode 100644
index 00000000..5b44089f
--- /dev/null
+++ b/arch/loongarch64/syscall_arch.h
@@ -0,0 +1,121 @@
+#define IPC_64 0x0
+
+#define __SYSCALL_LL_E(x) (x)
+#define __SYSCALL_LL_O(x) (x)
+
+#define SYSCALL_CLOBBERLIST \
+	"$t0", "$t1", "$t2", "$t3", \
+	"$t4", "$t5", "$t6", "$t7", "$t8", "memory"
+
+static inline long __syscall0(long n)
+{
+	register long a0 __asm__("$a0");
+	register long a7 __asm__("$a7") = n;
+
+	__asm__ __volatile__ (
+		"syscall 0"
+		: "+&r"(a0)
+		: "r"(a7)
+		: SYSCALL_CLOBBERLIST);
+	return a0;
+}
+
+static inline long __syscall1(long n, long a)
+{
+	register long a0 __asm__("$a0") = a;
+	register long a7 __asm__("$a7") = n;
+
+	__asm__ __volatile__ (
+		"syscall 0"
+		: "+&r"(a0)
+		: "r"(a7)
+		: SYSCALL_CLOBBERLIST);
+	return a0;
+}
+
+static inline long __syscall2(long n, long a, long b)
+{
+	register long a0 __asm__("$a0") = a;
+	register long a1 __asm__("$a1") = b;
+	register long a7 __asm__("$a7") = n;
+
+	__asm__ __volatile__ (
+		"syscall 0"
+		: "+&r"(a0)
+	        : "r"(a7), "r"(a1)
+		: SYSCALL_CLOBBERLIST);
+	return a0;
+}
+
+static inline long __syscall3(long n, long a, long b, long c)
+{
+	register long a0 __asm__("$a0") = a;
+	register long a1 __asm__("$a1") = b;
+	register long a2 __asm__("$a2") = c;
+	register long a7 __asm__("$a7") = n;
+
+	__asm__ __volatile__ (
+		"syscall 0"
+		: "+&r"(a0)
+	        : "r"(a7), "r"(a1), "r"(a2)
+		: SYSCALL_CLOBBERLIST);
+	return a0;
+}
+
+static inline long __syscall4(long n, long a, long b, long c, long d)
+{
+	register long a0 __asm__("$a0") = a;
+	register long a1 __asm__("$a1") = b;
+	register long a2 __asm__("$a2") = c;
+	register long a3 __asm__("$a3") = d;
+	register long a7 __asm__("$a7") = n;
+
+	__asm__ __volatile__ (
+		"syscall 0"
+		: "+&r"(a0)
+	        : "r"(a7), "r"(a1), "r"(a2), "r"(a3)
+		: SYSCALL_CLOBBERLIST);
+	return a0;
+}
+
+static inline long __syscall5(long n, long a, long b, long c, long d, long e)
+{
+	register long a0 __asm__("$a0") = a;
+	register long a1 __asm__("$a1") = b;
+	register long a2 __asm__("$a2") = c;
+	register long a3 __asm__("$a3") = d;
+	register long a4 __asm__("$a4") = e;
+	register long a7 __asm__("$a7") = n;
+
+	__asm__ __volatile__ (
+		"syscall 0"
+		: "+&r"(a0)
+	        : "r"(a7), "r"(a1), "r"(a2), "r"(a3), "r"(a4)
+		: SYSCALL_CLOBBERLIST);
+	return a0;
+}
+
+static inline long __syscall6(long n, long a, long b, long c, long d, long e, long f)
+{
+	register long a0 __asm__("$a0") = a;
+	register long a1 __asm__("$a1") = b;
+	register long a2 __asm__("$a2") = c;
+	register long a3 __asm__("$a3") = d;
+	register long a4 __asm__("$a4") = e;
+	register long a5 __asm__("$a5") = f;
+	register long a7 __asm__("$a7") = n;
+
+	__asm__ __volatile__ (
+		"syscall 0"
+		: "+&r"(a0)
+	        : "r"(a7), "r"(a1), "r"(a2), "r"(a3), "r"(a4), "r"(a5)
+		: SYSCALL_CLOBBERLIST);
+	return a0;
+}
+
+#define VDSO_USEFUL
+#define VDSO_CGT_SYM "__vdso_clock_gettime"
+#define VDSO_CGT_VER "LINUX_2.6"
+
+#define SO_SNDTIMEO_OLD 21
+#define SO_RCVTIMEO_OLD 20
diff --git a/configure b/configure
index a5231a0e..54b7aa2b 100755
--- a/configure
+++ b/configure
@@ -338,6 +338,7 @@ powerpc*|ppc*) ARCH=powerpc ;;
 riscv64*) ARCH=riscv64 ;;
 sh[1-9bel-]*|sh|superh*) ARCH=sh ;;
 s390x*) ARCH=s390x ;;
+loongarch64*) ARCH=loongarch64 ;;
 unknown) fail "$0: unable to detect target arch; try $0 --target=..." ;;
 *) fail "$0: unknown or unsupported target \"$target\"" ;;
 esac
diff --git a/crt/loongarch64/crti.s b/crt/loongarch64/crti.s
new file mode 100644
index 00000000..77dc262e
--- /dev/null
+++ b/crt/loongarch64/crti.s
@@ -0,0 +1,15 @@
+.section .init
+.global _init
+.align 3
+_init:
+	addi.d	$r3,$r3,-32
+	st.d	$r31,$r3,16
+	st.d	$r1,$r3,24
+
+.section .fini
+.global _fini
+.align 3
+_fini:
+	addi.d	$r3,$r3,-32
+	st.d	$r31,$r3,16
+	st.d	$r1,$r3,24
diff --git a/crt/loongarch64/crtn.s b/crt/loongarch64/crtn.s
new file mode 100644
index 00000000..12c27c66
--- /dev/null
+++ b/crt/loongarch64/crtn.s
@@ -0,0 +1,12 @@
+.section .init
+	ld.d	$r31,$r3,16
+	ld.d	$r1,$r3,24
+	addi.d	$r3,$r3,32
+	jirl	$r0,$r1,0
+
+
+.section .fini
+	ld.d	$r31,$r3,16
+	ld.d	$r1,$r3,24
+	addi.d	$r3,$r3,32
+	jirl	$r0,$r1,0
diff --git a/include/elf.h b/include/elf.h
index 5170f3e2..47a86615 100644
--- a/include/elf.h
+++ b/include/elf.h
@@ -696,6 +696,10 @@ typedef struct {
 #define NT_MIPS_FP_MODE	0x801
 #define NT_MIPS_MSA	0x802
 #define NT_VERSION	1
+#define NT_LOONGARCH_CPUCFG     0x900           /* Loongarch CPU config registers */
+#define NT_LOONGARCH_LBT        0x901           /* Loongarch Loongson Binary Translation registers */
+#define NT_LOONGARCH_LSX        0x902           /* Loongarch Loongson SIMD Extension registers */
+#define NT_LOONGARCH_LASX       0x903           /* Loongarch Loongson Advanced SIMD Extension registers */
 
 
 
@@ -3287,6 +3291,67 @@ enum
 #define R_RISCV_SET32           56
 #define R_RISCV_32_PCREL        57
 
+/* LoongISA ELF Flags */
+#define EM_LOONGARCH  258
+#define EF_LOONGARCH_ABI             0x0003
+#define EF_LOONGARCH_ABI_LP64        0x0003
+#define EF_LOONGARCH_ABI_LPX32       0x0002
+#define EF_LOONGARCH_ABI_LP32        0x0001
+
+/* Loongarch specific dynamic relocations. */
+#define R_LOONGARCH_NONE                        0
+#define R_LOONGARCH_32                          1
+#define R_LOONGARCH_64                          2
+#define R_LOONGARCH_RELATIVE                    3
+#define R_LOONGARCH_COPY                        4
+#define R_LOONGARCH_JUMP_SLOT                   5
+#define R_LOONGARCH_TLS_DTPMOD32                6
+#define R_LOONGARCH_TLS_DTPMOD64                7
+#define R_LOONGARCH_TLS_DTPREL32                8
+#define R_LOONGARCH_TLS_DTPREL64                9
+#define R_LOONGARCH_TLS_TPREL32                 10
+#define R_LOONGARCH_TLS_TPREL64                 11
+#define R_LOONGARCH_IRELATIVE                   12
+#define R_LOONGARCH_MARK_LA                     20
+#define R_LOONGARCH_MARK_PCREL                  21
+#define R_LOONGARCH_SOP_PUSH_PCREL              22
+#define R_LOONGARCH_SOP_PUSH_ABSOLUTE           23
+#define R_LOONGARCH_SOP_PUSH_DUP                24
+#define R_LOONGARCH_SOP_PUSH_GPREL              25
+#define R_LOONGARCH_SOP_PUSH_TLS_TPREL          26
+#define R_LOONGARCH_SOP_PUSH_TLS_GOT            27
+#define R_LOONGARCH_SOP_PUSH_TLS_GD             28
+#define R_LOONGARCH_SOP_PUSH_PLT_PCREL          29
+#define R_LOONGARCH_SOP_ASSERT                  30
+#define R_LOONGARCH_SOP_NOT                     31
+#define R_LOONGARCH_SOP_SUB                     32
+#define R_LOONGARCH_SOP_SL                      33
+#define R_LOONGARCH_SOP_SR                      34
+#define R_LOONGARCH_SOP_ADD                     35
+#define R_LOONGARCH_SOP_AND                     36
+#define R_LOONGARCH_SOP_IF_ELSE                 37
+#define R_LOONGARCH_SOP_POP_32_S_10_5           38
+#define R_LOONGARCH_SOP_POP_32_U_10_12          39
+#define R_LOONGARCH_SOP_POP_32_S_10_12          40
+#define R_LOONGARCH_SOP_POP_32_S_10_16          41
+#define R_LOONGARCH_SOP_POP_32_S_10_16_S2       42
+#define R_LOONGARCH_SOP_POP_32_S_5_20           43
+#define R_LOONGARCH_SOP_POP_32_S_0_5_10_16_S2   44
+#define R_LOONGARCH_SOP_POP_32_S_0_10_10_16_S2  45
+#define R_LOONGARCH_SOP_POP_32_U                46
+#define R_LOONGARCH_ADD8                        47
+#define R_LOONGARCH_ADD16                       48
+#define R_LOONGARCH_ADD24                       49
+#define R_LOONGARCH_ADD32                       50
+#define R_LOONGARCH_ADD64                       51
+#define R_LOONGARCH_SUB8                        52
+#define R_LOONGARCH_SUB16                       53
+#define R_LOONGARCH_SUB24                       54
+#define R_LOONGARCH_SUB32                       55
+#define R_LOONGARCH_SUB64                       56
+#define R_LOONGARCH_GNU_VTINHERIT               57
+#define R_LOONGARCH_GNU_VTENTRY                 58
+
 #ifdef __cplusplus
 }
 #endif
diff --git a/src/fenv/loongarch64/fenv-sf.c b/src/fenv/loongarch64/fenv-sf.c
new file mode 100644
index 00000000..6aa9b545
--- /dev/null
+++ b/src/fenv/loongarch64/fenv-sf.c
@@ -0,0 +1,3 @@
+#ifdef __loongarch64_soft_float
+#include "../fenv.c"
+#endif
diff --git a/src/fenv/loongarch64/fenv.S b/src/fenv/loongarch64/fenv.S
new file mode 100644
index 00000000..beb2868e
--- /dev/null
+++ b/src/fenv/loongarch64/fenv.S
@@ -0,0 +1,75 @@
+#ifndef __loongarch_soft_float
+
+.global	feclearexcept
+.type	feclearexcept,@function
+feclearexcept:
+	//andi	$a0, $a0, 0x1f0000 // la: exception bits in 16-20 bit of fcsr0.
+        li      $a1, 0x1f0000
+        and     $a0, $a0, $a1
+	movfcsr2gr $a1, $r0 // r0 is fpu control status register 0(fcsr0), r0 -> fcsr0, r1 -> fcsr1, r2 -> fcsr2, r3 - fcsr3
+	or	$a1, $a1, $a0
+	xor	$a1, $a1, $a0
+	movgr2fcsr $r0, $a1
+        li      $v0, 0
+	jr	$ra
+
+.global	feraiseexcept
+.type	feraiseexcept,@function
+feraiseexcept:
+	//andi	$a0, $a0, 0x1f0000
+        li      $a1, 0x1f0000
+        and     $a0, $a0, $a1
+	movfcsr2gr $a1, $r0
+	or	$a1, $a1, $a0
+	movgr2fcsr $r0, $a1
+        li      $v0, 0
+	jr	$ra
+
+.global	fetestexcept
+.type	fetestexcept,@function
+fetestexcept:
+	//andi	$a0, $a0, 0x1f0000
+        li      $a1, 0x1f0000
+        and     $a0, $a0, $a1
+	movfcsr2gr $a1, $r0
+        and     $v0, $a1, $a0
+	jr	$ra
+
+.global	fegetround
+.type	fegetround,@function
+fegetround:
+	movfcsr2gr $v0, $r0
+        andi    $v0, $v0, 0x300 // RM
+	jr	$ra
+
+.global	__fesetround
+.hidden __fesetround
+.type	__fesetround,@function
+__fesetround:
+	movfcsr2gr $a1, $r0
+	li	$a2, -769
+	and	$a1, $a1, $a2
+	or	$a1, $a1, $a0
+	movgr2fcsr $r0, $a1
+        li      $v0, 0
+	jr	$ra
+
+.global	fegetenv
+.type	fegetenv,@function
+fegetenv:
+	movfcsr2gr $a1, $r0
+	st.w	$a1, $a0, 0
+        li      $v0, 0
+	jr	$ra
+
+.global	fesetenv
+.type	fesetenv,@function
+fesetenv:
+	addi.d	$a1, $a0, 1
+	beq	$a1, $r0, 1f
+	ld.w	$a1, $a0, 0
+1:	movgr2fcsr $r0, $a1
+        li      $v0, 0
+	jr	$ra
+
+#endif
diff --git a/src/ldso/loongarch64/dlsym.s b/src/ldso/loongarch64/dlsym.s
new file mode 100644
index 00000000..2faa8ed3
--- /dev/null
+++ b/src/ldso/loongarch64/dlsym.s
@@ -0,0 +1,12 @@
+.global dlsym
+.hidden __dlsym
+.type   dlsym,@function
+dlsym:
+	move	$r6, $ra
+	la.global	$r16, __dlsym
+	addi.d 	$sp, $sp, -32
+	st.d	$ra, $sp, 24
+	jirl	$ra, $r16, 0
+	ld.d	$ra, $sp, 24
+	addi.d	$sp, $sp, 32
+	jr	$ra
diff --git a/src/setjmp/loongarch64/longjmp.S b/src/setjmp/loongarch64/longjmp.S
new file mode 100644
index 00000000..90529b8c
--- /dev/null
+++ b/src/setjmp/loongarch64/longjmp.S
@@ -0,0 +1,37 @@
+.global    _longjmp
+.global    longjmp
+.type    _longjmp,@function
+.type    longjmp,@function
+_longjmp:
+longjmp:
+	add.d   $t5, $a0, $zero
+	add.d   $v0, $a1, $zero
+	
+	bne     $v0, $zero, 1f
+	addi.d  $v0, $v0, 1
+
+1:
+	ld.d    $ra, $t5, 0
+	ld.d    $sp, $t5, 8
+	ld.d    $fp, $t5, 16
+	ld.d    $s0, $t5, 24
+	ld.d    $s1, $t5, 32
+	ld.d    $s2, $t5, 40
+	ld.d    $s3, $t5, 48
+	ld.d    $s4, $t5, 56
+	ld.d    $s5, $t5, 64
+	ld.d    $s6, $t5, 72
+	ld.d    $s7, $t5, 80
+	ld.d    $s8, $t5, 88
+#ifndef __loongarch64_soft_float
+	fld.d   $fs0, $t5, 96
+	fld.d   $fs1, $t5, 104
+	fld.d   $fs2, $t5, 112
+	fld.d   $fs3, $t5, 120
+	fld.d   $fs4, $t5, 128
+	fld.d   $fs5, $t5, 136
+	fld.d   $fs6, $t5, 144
+	fld.d   $fs7, $t5, 152
+#endif
+	jirl    $zero, $ra, 0
+
diff --git a/src/setjmp/loongarch64/setjmp.S b/src/setjmp/loongarch64/setjmp.S
new file mode 100644
index 00000000..83170dea
--- /dev/null
+++ b/src/setjmp/loongarch64/setjmp.S
@@ -0,0 +1,35 @@
+.global    __setjmp
+.global    _setjmp
+.global    setjmp
+.type    __setjmp,@function
+.type    _setjmp,@function
+.type    setjmp,@function
+__setjmp:
+_setjmp:
+setjmp:
+	st.d    $ra, $a0, 0
+	st.d    $sp, $a0, 8
+	
+	st.d    $fp, $a0, 16
+	st.d    $s0, $a0, 24
+	st.d    $s1, $a0, 32
+	st.d    $s2, $a0, 40
+	st.d    $s3, $a0, 48
+	st.d    $s4, $a0, 56
+	st.d    $s5, $a0, 64
+	st.d    $s6, $a0, 72
+	st.d    $s7, $a0, 80
+	st.d    $s8, $a0, 88
+#ifndef __loongarch64_soft_float
+	fst.d   $fs0, $a0, 96
+	fst.d   $fs1, $a0, 104
+	fst.d   $fs2, $a0, 112
+	fst.d   $fs3, $a0, 120
+	fst.d   $fs4, $a0, 128
+	fst.d   $fs5, $a0, 136
+	fst.d   $fs6, $a0, 144
+	fst.d   $fs7, $a0, 152
+#endif
+	xor     $v0, $v0, $v0
+	jirl    $zero, $ra, 0
+
diff --git a/src/signal/loongarch64/restore.s b/src/signal/loongarch64/restore.s
new file mode 100644
index 00000000..9bf015a0
--- /dev/null
+++ b/src/signal/loongarch64/restore.s
@@ -0,0 +1,10 @@
+.global	__restore_rt
+.global	__restore
+.hidden __restore_rt
+.hidden __restore
+.type	__restore_rt,@function
+.type	__restore,@function
+__restore_rt:
+__restore:
+	ori	$a7, $zero, 139
+	syscall	0
diff --git a/src/signal/loongarch64/sigsetjmp.s b/src/signal/loongarch64/sigsetjmp.s
new file mode 100644
index 00000000..e860c47b
--- /dev/null
+++ b/src/signal/loongarch64/sigsetjmp.s
@@ -0,0 +1,33 @@
+.global sigsetjmp
+.global __sigsetjmp
+.type   sigsetjmp,@function
+.type   __sigsetjmp,@function
+sigsetjmp:
+__sigsetjmp:
+        or $t5, $a0, $zero
+        or $t6, $a1, $zero
+
+        # comparing save mask with 0, if equals to 0 then
+        # sigsetjmp is equal to setjmp.
+        beq     $t6, $zero, 1f
+        st.d    $ra, $t5, 160
+        st.d    $s0, $t5, 168
+
+        # save base of got so that we can use it later
+        # once we return from 'longjmp'
+        la.global       $t8, setjmp
+        or      $s0, $a0, $zero
+        jirl    $ra, $t8, 0
+
+        or      $v1, $v0, $zero         # Return from 'setjmp' or 'longjmp'
+        ld.d    $ra, $t5, 160   # Restore ra of sigsetjmp
+        ld.d    $s0, $t5, 168   # Restore $s0 of sigsetjmp
+        or      $a0, $t5, $zero
+
+.hidden __sigsetjmp_tail
+        la.global       $t8, __sigsetjmp_tail
+        jr      $t8
+1:
+        la.global       $t8, setjmp
+        jr      $t8
+
diff --git a/src/thread/loongarch64/__set_thread_area.s b/src/thread/loongarch64/__set_thread_area.s
new file mode 100644
index 00000000..891ac076
--- /dev/null
+++ b/src/thread/loongarch64/__set_thread_area.s
@@ -0,0 +1,7 @@
+.global	__set_thread_area
+.type	__set_thread_area, @function
+__set_thread_area:
+	or	$tp, $a0, $zero
+	ori	$a0, $zero, 0
+	jirl	$zero, $ra, 0
+
diff --git a/src/thread/loongarch64/__unmapself.s b/src/thread/loongarch64/__unmapself.s
new file mode 100644
index 00000000..e0d2fcf6
--- /dev/null
+++ b/src/thread/loongarch64/__unmapself.s
@@ -0,0 +1,8 @@
+.global	__unmapself
+.type	__unmapself, @function
+__unmapself:
+	ori	$a7, $zero, 215
+	syscall	0				# call munmap
+	ori	$a0, $zero, 0
+	ori	$a7, $zero, 93
+	syscall	0				# call exit
diff --git a/src/thread/loongarch64/clone.s b/src/thread/loongarch64/clone.s
new file mode 100644
index 00000000..a3fd82ba
--- /dev/null
+++ b/src/thread/loongarch64/clone.s
@@ -0,0 +1,27 @@
+.global	__clone
+.hidden __clone
+.type	__clone,@function
+__clone:
+	# Save function pointer and argument pointer on new thread stack
+	addi.d	$a1, $a1, -16	# aligning stack to double word
+	st.d	$a0, $a1, 0		# save function pointer
+	st.d	$a3, $a1, 8		# save argument pointer
+
+	# Shuffle (fn,sp,fl,arg,ptid,tls,ctid) to (fl,sp,ptid,tls,ctid)
+	# sys_clone(u64 flags, u64 ustack_base, u64 parent_tidptr, u64 child_tidptr, u64 tls)
+	or	$a0, $a2, $zero
+	or	$a2, $a4, $zero
+	or	$a3, $a6, $zero
+	or	$a4, $a5, $zero
+	ori	$a7, $zero, 220
+	syscall 0				# call clone
+
+	beqz	$a0, 1f			# whether child process
+	jirl	$zero, $ra, 0	# parent process return
+1:
+	ld.d	$t8, $sp, 0     # function pointer
+	ld.d	$a0, $sp, 8     # argument pointer
+	jirl	$ra, $t8, 0     # call the user's function
+	ori	$a7, $zero, 93
+	syscall	0				# child process exit
+
diff --git a/src/thread/loongarch64/syscall_cp.s b/src/thread/loongarch64/syscall_cp.s
new file mode 100644
index 00000000..d833f625
--- /dev/null
+++ b/src/thread/loongarch64/syscall_cp.s
@@ -0,0 +1,34 @@
+.global	__cp_begin
+.hidden	__cp_begin
+.type	__cp_begin,@function
+.global	__cp_end
+.hidden	__cp_end
+.type	__cp_end,@function
+.global	__cp_cancel
+.hidden	__cp_cancel
+.type	__cp_cancel,@function
+.hidden	__cancel
+.global	__syscall_cp_asm
+.hidden	__syscall_cp_asm
+.type	__syscall_cp_asm,@function
+
+__syscall_cp_asm:
+__cp_begin:
+	ld.w	$a0, $a0, 0
+	bnez	$a0, __cp_cancel
+	or	$t8, $a1, $zero     # reserve system call number
+	or	$a0, $a2, $zero
+	or	$a1, $a3, $zero
+	or	$a2, $a4, $zero
+	or	$a3, $a5, $zero
+	or	$a4, $a6, $zero
+	or	$a5, $a7, $zero
+	ld.d	$a6, $sp, 0
+	or	$a7, $t8, $zero
+	syscall	0
+__cp_end:
+	jirl	$zero, $ra, 0
+__cp_cancel:
+	la.local $t8, __cancel
+	jirl	$zero, $t8, 0
+
diff --git a/src/unistd/loongarch64/pipe.s b/src/unistd/loongarch64/pipe.s
new file mode 100644
index 00000000..b7f5b7b4
--- /dev/null
+++ b/src/unistd/loongarch64/pipe.s
@@ -0,0 +1,12 @@
+.global pipe
+.type   pipe,@function
+pipe:
+	move	$a1, $r0
+	li	$a7, 59
+	syscall	0
+	li	$t0, -4096
+	bgeu	$t0, $v0, 1f
+	la.global	$t1, __syscall_ret
+	jr	$t1
+1:	move	$v0, $r0
+	jr	$ra
-- 
2.20.1


^ permalink raw reply	[flat|nested] 14+ messages in thread

* Re: Re: [musl] Port the new architecture loongarch64 to musl
  2021-06-24 11:43   ` 翟小娟
@ 2021-06-24 11:56     ` 罗勇刚(Yonggang Luo)
  2021-06-24 12:17       ` 翟小娟
  0 siblings, 1 reply; 14+ messages in thread
From: 罗勇刚(Yonggang Luo) @ 2021-06-24 11:56 UTC (permalink / raw)
  To: Musl

[-- Attachment #1: Type: text/plain, Size: 2470 bytes --]

On Thu, Jun 24, 2021 at 7:43 PM 翟小娟 <zhaixiaojuan@loongson.cn> wrote:
>
> Hi, qemu supports loongarch64 architecture has been completed:
https://github.com/loongson/qemu .

Good to hear that, which qemu branches support for loongarch64?

> For musl loongarch64 source code can also be obtained from
https://github.com/loongson-community/musl. If necessary, we can also
provide a remote testing enviroment.
> See the attachment for specific modifications.
>
> -----原始邮件-----
> 发件人:"罗勇刚(Yonggang Luo)" <luoyonggang@gmail.com>
> 发送时间:2021-05-08 00:29:40 (星期六)
> 收件人: Musl <musl@lists.openwall.com>
> 抄送: "陈国祺" <chenguoqi@loongson.cn>
> 主题: Re: [musl] Port the new architecture loongarch64 to musl
>
> Same question, does qemu have already support for  loongarch64, that's
means a lot for auto testing
> As the real hardware will be not broadly  available in the next few years.
>
>
>
> On Fri, May 7, 2021 at 5:01 PM 翟小娟 <zhaixiaojuan@loongson.cn> wrote:
> Hi,
> I ported a new architecture loongarch64 on the latest branch of musl
master. It has been successfully compiled and run the official test
libraries libc-testsuit and libc-test of musl.
> The source code of the prot has been published in
https://github.com/loongson-community/musl.  Or check the attachment
0001-port-to-loongarch64.patch, it is the transplanted patch file.
>
> Introduction to loongarch architecture:
> The Loongarch architecture is a simplified instruction computer style
instruction system architecture. The instruction length is fixed and the
encoding format is regular. Most instructions have only two source operands
and one destination operand. The load/store architecture is adopted, that
is, only load/store memory access instructions can access the memory, and
the operation objects of other instructions are all It is the immediate
value in the register or instruction code in the processor core.
> The Loongson architecture is divided into two versions, 32bit and 64bit,
called LA32 and LA64 respectively. LA64 architecture application level is
downward binary compatible with LA32 architecture.
>
>
>
> --
> 此致
> 礼
> 罗勇刚
> Yours
> sincerely,
> Yonggang Luo
>
>
> </zhaixiaojuan@loongson.cn></chenguoqi@loongson.cn></
musl@lists.openwall.com></luoyonggang@gmail.com>



--
         此致
礼
罗勇刚
Yours
    sincerely,
Yonggang Luo

[-- Attachment #2: Type: text/html, Size: 3350 bytes --]

^ permalink raw reply	[flat|nested] 14+ messages in thread

* Re: Re: Re: [musl] Port the new architecture loongarch64 to musl
  2021-06-24 11:56     ` 罗勇刚(Yonggang Luo)
@ 2021-06-24 12:17       ` 翟小娟
  2021-06-24 12:47         ` 罗勇刚(Yonggang Luo)
  0 siblings, 1 reply; 14+ messages in thread
From: 翟小娟 @ 2021-06-24 12:17 UTC (permalink / raw)
  To: musl

[-- Attachment #1: Type: text/plain, Size: 2966 bytes --]

Hi, 
Qemu Loongarch64 related code can be viewed https://github.com/loongson/qemu/pulls (Add loongarch linux-user emulation support)


-----原始邮件-----
发件人:"罗勇刚(Yonggang Luo)" <luoyonggang@gmail.com>
发送时间:2021-06-24 19:56:17 (星期四)
收件人: Musl <musl@lists.openwall.com>
抄送: 
主题: Re: Re: [musl] Port the new architecture loongarch64 to musl



On Thu, Jun 24, 2021 at 7:43 PM 翟小娟 <zhaixiaojuan@loongson.cn> wrote:
&gt;
&gt; Hi, qemu supports loongarch64 architecture has been completed: https://github.com/loongson/qemu .

Good to hear that, which qemu branches support for loongarch64?

&gt; For musl loongarch64 source code can also be obtained from https://github.com/loongson-community/musl. If necessary, we can also provide a remote testing enviroment.
&gt; See the attachment for specific modifications.
&gt;
&gt; -----原始邮件-----
&gt; 发件人:"罗勇刚(Yonggang Luo)" <luoyonggang@gmail.com>
&gt; 发送时间:2021-05-08 00:29:40 (星期六)
&gt; 收件人: Musl <musl@lists.openwall.com>
&gt; 抄送: "陈国祺" <chenguoqi@loongson.cn>
&gt; 主题: Re: [musl] Port the new architecture loongarch64 to musl
&gt;
&gt; Same question, does qemu have already support for  loongarch64, that's means a lot for auto testing
&gt; As the real hardware will be not broadly  available in the next few years.
&gt;
&gt;
&gt;
&gt; On Fri, May 7, 2021 at 5:01 PM 翟小娟 <zhaixiaojuan@loongson.cn> wrote:
&gt; Hi,
&gt; I ported a new architecture loongarch64 on the latest branch of musl master. It has been successfully compiled and run the official test libraries libc-testsuit and libc-test of musl.
&gt; The source code of the prot has been published in https://github.com/loongson-community/musl.  Or check the attachment 0001-port-to-loongarch64.patch, it is the transplanted patch file.
&gt;
&gt; Introduction to loongarch architecture:
&gt; The Loongarch architecture is a simplified instruction computer style instruction system architecture. The instruction length is fixed and the encoding format is regular. Most instructions have only two source operands and one destination operand. The load/store architecture is adopted, that is, only load/store memory access instructions can access the memory, and the operation objects of other instructions are all It is the immediate value in the register or instruction code in the processor core.
&gt; The Loongson architecture is divided into two versions, 32bit and 64bit, called LA32 and LA64 respectively. LA64 architecture application level is downward binary compatible with LA32 architecture.
&gt;
&gt;
&gt;
&gt; --
&gt; 此致
&gt; 礼
&gt; 罗勇刚
&gt; Yours
&gt; sincerely,
&gt; Yonggang Luo
&gt;
&gt;
&gt; </zhaixiaojuan@loongson.cn></chenguoqi@loongson.cn></musl@lists.openwall.com></luoyonggang@gmail.com>



--
此致
礼
罗勇刚
Yours
sincerely,
Yonggang Luo


</zhaixiaojuan@loongson.cn></musl@lists.openwall.com></luoyonggang@gmail.com>

[-- Warning: decoded text below may be mangled, UTF-8 assumed --]
[-- Attachment #2: 0001-port-to-loongarch64.patch --]
[-- Type: text/x-patch; name=0001-port-to-loongarch64.patch, Size: 53991 bytes --]

From 137506d1039e0800c6c2631df16f1584c0f64b07 Mon Sep 17 00:00:00 2001
From: zhaixiaojuan <zhaixiaojuan@loongson.cn>
Date: Fri, 7 May 2021 15:35:11 +0800
Subject: [PATCH] port to loongarch64

Signed-off-by: zhaixiaojuan <zhaixiaojuan@loongson.cn>
---
 arch/loongarch64/atomic_arch.h             |  52 ++++
 arch/loongarch64/bits/alltypes.h.in        |  20 ++
 arch/loongarch64/bits/fcntl.h              |  40 +++
 arch/loongarch64/bits/fenv.h               |  25 ++
 arch/loongarch64/bits/float.h              |  16 ++
 arch/loongarch64/bits/hwcap.h              |  15 ++
 arch/loongarch64/bits/posix.h              |   2 +
 arch/loongarch64/bits/ptrace.h             |   4 +
 arch/loongarch64/bits/reg.h                |  66 +++++
 arch/loongarch64/bits/resource.h           |   5 +
 arch/loongarch64/bits/setjmp.h             |   1 +
 arch/loongarch64/bits/signal.h             | 144 ++++++++++
 arch/loongarch64/bits/stat.h               |  20 ++
 arch/loongarch64/bits/statfs.h             |   6 +
 arch/loongarch64/bits/stdint.h             |  20 ++
 arch/loongarch64/bits/syscall.h.in         | 291 +++++++++++++++++++++
 arch/loongarch64/bits/user.h               |   5 +
 arch/loongarch64/crt_arch.h                |  23 ++
 arch/loongarch64/ksigaction.h              |  13 +
 arch/loongarch64/kstat.h                   |  22 ++
 arch/loongarch64/pthread_arch.h            |  13 +
 arch/loongarch64/reloc.h                   |  43 +++
 arch/loongarch64/syscall_arch.h            | 121 +++++++++
 configure                                  |   1 +
 crt/loongarch64/crti.s                     |  15 ++
 crt/loongarch64/crtn.s                     |  12 +
 include/elf.h                              |  65 +++++
 src/fenv/loongarch64/fenv-sf.c             |   3 +
 src/fenv/loongarch64/fenv.S                |  75 ++++++
 src/ldso/loongarch64/dlsym.s               |  12 +
 src/setjmp/loongarch64/longjmp.S           |  37 +++
 src/setjmp/loongarch64/setjmp.S            |  35 +++
 src/signal/loongarch64/restore.s           |  10 +
 src/signal/loongarch64/sigsetjmp.s         |  33 +++
 src/thread/loongarch64/__set_thread_area.s |   7 +
 src/thread/loongarch64/__unmapself.s       |   8 +
 src/thread/loongarch64/clone.s             |  27 ++
 src/thread/loongarch64/syscall_cp.s        |  34 +++
 src/unistd/loongarch64/pipe.s              |  12 +
 39 files changed, 1353 insertions(+)
 create mode 100644 arch/loongarch64/atomic_arch.h
 create mode 100644 arch/loongarch64/bits/alltypes.h.in
 create mode 100644 arch/loongarch64/bits/fcntl.h
 create mode 100644 arch/loongarch64/bits/fenv.h
 create mode 100644 arch/loongarch64/bits/float.h
 create mode 100644 arch/loongarch64/bits/hwcap.h
 create mode 100644 arch/loongarch64/bits/posix.h
 create mode 100644 arch/loongarch64/bits/ptrace.h
 create mode 100644 arch/loongarch64/bits/reg.h
 create mode 100644 arch/loongarch64/bits/resource.h
 create mode 100644 arch/loongarch64/bits/setjmp.h
 create mode 100644 arch/loongarch64/bits/signal.h
 create mode 100644 arch/loongarch64/bits/stat.h
 create mode 100644 arch/loongarch64/bits/statfs.h
 create mode 100644 arch/loongarch64/bits/stdint.h
 create mode 100644 arch/loongarch64/bits/syscall.h.in
 create mode 100644 arch/loongarch64/bits/user.h
 create mode 100644 arch/loongarch64/crt_arch.h
 create mode 100644 arch/loongarch64/ksigaction.h
 create mode 100644 arch/loongarch64/kstat.h
 create mode 100644 arch/loongarch64/pthread_arch.h
 create mode 100644 arch/loongarch64/reloc.h
 create mode 100644 arch/loongarch64/syscall_arch.h
 create mode 100644 crt/loongarch64/crti.s
 create mode 100644 crt/loongarch64/crtn.s
 create mode 100644 src/fenv/loongarch64/fenv-sf.c
 create mode 100644 src/fenv/loongarch64/fenv.S
 create mode 100644 src/ldso/loongarch64/dlsym.s
 create mode 100644 src/setjmp/loongarch64/longjmp.S
 create mode 100644 src/setjmp/loongarch64/setjmp.S
 create mode 100644 src/signal/loongarch64/restore.s
 create mode 100644 src/signal/loongarch64/sigsetjmp.s
 create mode 100644 src/thread/loongarch64/__set_thread_area.s
 create mode 100644 src/thread/loongarch64/__unmapself.s
 create mode 100644 src/thread/loongarch64/clone.s
 create mode 100644 src/thread/loongarch64/syscall_cp.s
 create mode 100644 src/unistd/loongarch64/pipe.s

diff --git a/arch/loongarch64/atomic_arch.h b/arch/loongarch64/atomic_arch.h
new file mode 100644
index 00000000..eb2dedda
--- /dev/null
+++ b/arch/loongarch64/atomic_arch.h
@@ -0,0 +1,52 @@
+#define LLSC_M "m"
+
+#define a_ll a_ll
+static inline int a_ll(volatile int *p)
+{
+	int v;
+	__asm__ __volatile__ (
+		"ll.w %0, %1"
+		: "=r"(v) : LLSC_M(*p));
+	return v;
+}
+
+#define a_sc a_sc
+static inline int a_sc(volatile int *p, int v)
+{
+	int r;
+	__asm__ __volatile__ (
+		"sc.w %0, %1"
+		: "=r"(r), "="LLSC_M(*p) : "0"(v) : "memory");
+	return r;
+}
+
+#define a_ll_p a_ll_p
+static inline void *a_ll_p(volatile void *p)
+{
+	void *v;
+	__asm__ __volatile__ (
+		"ll.d %0, %1"
+		: "=r"(v) : LLSC_M(*(void *volatile *)p));
+	return v;
+}
+
+#define a_sc_p a_sc_p
+static inline int a_sc_p(volatile void *p, void *v)
+{
+	long r;
+	__asm__ __volatile__ (
+		"sc.d %0, %1"
+		: "=r"(r), "="LLSC_M(*(void *volatile *)p) : "0"(v) : "memory");
+	return r;
+}
+
+#define a_barrier a_barrier
+static inline void a_barrier()
+{
+	__asm__ __volatile__ ("dbar 0" : : : "memory");
+}
+
+#define a_pre_llsc a_barrier
+#define a_post_llsc a_barrier
+
+#undef LLSC_M
diff --git a/arch/loongarch64/bits/alltypes.h.in b/arch/loongarch64/bits/alltypes.h.in
new file mode 100644
index 00000000..38871b5f
--- /dev/null
+++ b/arch/loongarch64/bits/alltypes.h.in
@@ -0,0 +1,20 @@
+#define _Addr long
+#define _Int64 long
+#define _Reg long
+
+#define __BYTE_ORDER 1234
+#define __LONG_MAX 0x7fffffffffffffffL
+
+TYPEDEF __builtin_va_list va_list;
+TYPEDEF __builtin_va_list __isoc_va_list;
+
+#ifndef __cplusplus
+TYPEDEF int wchar_t;
+#endif
+
+TYPEDEF float float_t;
+TYPEDEF double double_t;
+
+TYPEDEF struct { long long __ll; long double __ld; } max_align_t;
+
+TYPEDEF unsigned nlink_t;
diff --git a/arch/loongarch64/bits/fcntl.h b/arch/loongarch64/bits/fcntl.h
new file mode 100644
index 00000000..9bcbb7ff
--- /dev/null
+++ b/arch/loongarch64/bits/fcntl.h
@@ -0,0 +1,40 @@
+#define O_CREAT        0100
+#define O_EXCL         0200
+#define O_NOCTTY       0400
+#define O_TRUNC       01000
+#define O_APPEND      02000
+#define O_NONBLOCK    04000
+#define O_DSYNC      010000
+#define O_SYNC     04010000
+#define O_RSYNC    04010000
+#define O_DIRECTORY 0200000
+#define O_NOFOLLOW  0400000
+#define O_CLOEXEC  02000000
+
+#define O_ASYNC      020000
+#define O_DIRECT     040000
+#define O_LARGEFILE 0100000
+#define O_NOATIME  01000000
+#define O_PATH    010000000
+#define O_TMPFILE 020000000
+#define O_NDELAY O_NONBLOCK
+
+#define F_DUPFD  0
+#define F_GETFD  1
+#define F_SETFD  2
+#define F_GETFL  3
+#define F_SETFL  4
+
+#define F_SETOWN 8
+#define F_GETOWN 9
+#define F_SETSIG 10
+#define F_GETSIG 11
+
+#define F_GETLK  5
+#define F_SETLK  6
+#define F_SETLKW 7
+
+#define F_SETOWN_EX 15
+#define F_GETOWN_EX 16
+
+#define F_GETOWNER_UIDS 17
diff --git a/arch/loongarch64/bits/fenv.h b/arch/loongarch64/bits/fenv.h
new file mode 100644
index 00000000..6f98053a
--- /dev/null
+++ b/arch/loongarch64/bits/fenv.h
@@ -0,0 +1,25 @@
+#ifdef __loongarch_soft_float
+#define FE_ALL_EXCEPT 0
+#define FE_TONEAREST  0
+#else
+#define FE_INEXACT    0x010000
+#define FE_UNDERFLOW  0x020000
+#define FE_OVERFLOW   0x040000
+#define FE_DIVBYZERO  0x080000
+#define FE_INVALID    0x100000
+
+#define FE_ALL_EXCEPT 0x1F0000
+
+#define FE_TONEAREST  0x000
+#define FE_TOWARDZERO 0x100
+#define FE_UPWARD     0x200
+#define FE_DOWNWARD   0x300
+#endif
+
+typedef unsigned fexcept_t;
+
+typedef struct {
+	unsigned __cw;
+} fenv_t;
+
+#define FE_DFL_ENV ((const fenv_t *) -1)
diff --git a/arch/loongarch64/bits/float.h b/arch/loongarch64/bits/float.h
new file mode 100644
index 00000000..719c7908
--- /dev/null
+++ b/arch/loongarch64/bits/float.h
@@ -0,0 +1,16 @@
+#define FLT_EVAL_METHOD 0
+
+#define LDBL_TRUE_MIN 6.47517511943802511092443895822764655e-4966L
+#define LDBL_MIN 3.36210314311209350626267781732175260e-4932L
+#define LDBL_MAX 1.18973149535723176508575932662800702e+4932L
+#define LDBL_EPSILON 1.92592994438723585305597794258492732e-34L
+
+#define LDBL_MANT_DIG 113
+#define LDBL_MIN_EXP (-16381)
+#define LDBL_MAX_EXP 16384
+
+#define LDBL_DIG 33
+#define LDBL_MIN_10_EXP (-4931)
+#define LDBL_MAX_10_EXP 4932
+
+#define DECIMAL_DIG 36
diff --git a/arch/loongarch64/bits/hwcap.h b/arch/loongarch64/bits/hwcap.h
new file mode 100644
index 00000000..bb505da8
--- /dev/null
+++ b/arch/loongarch64/bits/hwcap.h
@@ -0,0 +1,15 @@
+/* HWCAP - Hardware Capabilities
+ * Hardware information is not clear at present, leave it blank. 
+ */
+#define HWCAP_LOONGARCH_CPUCFG	(1 << 0)
+#define HWCAP_LOONGARCH_FPU	(1 << 1)
+#define HWCAP_LOONGARCH_LSX	(1 << 2)  /* support 128bit vectors*/
+#define HWCAP_LOONGARCH_LASX	(1 << 3)  /* support 256bit vectors*/
+#define HWCAP_LOONGARCH_LBT	(1 << 4)  /* support LBT*/
+#define HWCAP_LOONGARCH_LVZ	(1 << 5)  /* support virtualization expansion*/
+#define HWCAP_LOONGARCH_CRC32	(1 << 7)  /* support CRC32 check*/
+#define HWCAP_LOONGARCH_AES	(1 << 6)
+#define HWCAP_LOONGARCH_SHA1	(1 << 8)
+#define HWCAP_LOONGARCH_SHA2	(1 << 9)
+#define HWCAP_LOONGARCH_SHA3	(1 << 10)
+
diff --git a/arch/loongarch64/bits/posix.h b/arch/loongarch64/bits/posix.h
new file mode 100644
index 00000000..8068ce98
--- /dev/null
+++ b/arch/loongarch64/bits/posix.h
@@ -0,0 +1,2 @@
+#define _POSIX_V6_LP64_OFF64 1
+#define _POSIX_V7_LP64_OFF64 1
diff --git a/arch/loongarch64/bits/ptrace.h b/arch/loongarch64/bits/ptrace.h
new file mode 100644
index 00000000..741fc668
--- /dev/null
+++ b/arch/loongarch64/bits/ptrace.h
@@ -0,0 +1,4 @@
+#define PTRACE_GET_THREAD_AREA	25
+#define PTRACE_SET_THREAD_AREA	26
+#define PTRACE_GET_WATCH_REGS	0xd0
+#define PTRACE_SET_WATCH_REGS	0xd1
diff --git a/arch/loongarch64/bits/reg.h b/arch/loongarch64/bits/reg.h
new file mode 100644
index 00000000..5d3f92c5
--- /dev/null
+++ b/arch/loongarch64/bits/reg.h
@@ -0,0 +1,66 @@
+#undef __WORDSIZE
+#define __WORDSIZE 64
+#define LOONGARCH64_EF_R0   0
+#define LOONGARCH64_EF_R1   1
+#define LOONGARCH64_EF_R2   2
+#define LOONGARCH64_EF_R3   3
+#define LOONGARCH64_EF_R4   4
+#define LOONGARCH64_EF_R5   5
+#define LOONGARCH64_EF_R6   6
+#define LOONGARCH64_EF_R7   7
+#define LOONGARCH64_EF_R8   8
+#define LOONGARCH64_EF_R9   9
+#define LOONGARCH64_EF_R10    10
+#define LOONGARCH64_EF_R11    11
+#define LOONGARCH64_EF_R12    12
+#define LOONGARCH64_EF_R13    13
+#define LOONGARCH64_EF_R14    14
+#define LOONGARCH64_EF_R15    15
+#define LOONGARCH64_EF_R16    16
+#define LOONGARCH64_EF_R17    17
+#define LOONGARCH64_EF_R18    18
+#define LOONGARCH64_EF_R19    19
+#define LOONGARCH64_EF_R20    20
+#define LOONGARCH64_EF_R21    21
+#define LOONGARCH64_EF_R22    22
+#define LOONGARCH64_EF_R23    23
+#define LOONGARCH64_EF_R24    24
+#define LOONGARCH64_EF_R25    25
+#define LOONGARCH64_EF_R26    26
+#define LOONGARCH64_EF_R27    27
+#define LOONGARCH64_EF_R28    28
+#define LOONGARCH64_EF_R29    29
+#define LOONGARCH64_EF_R30    30
+#define LOONGARCH64_EF_R31    31
+
+#define LOONGARCH64_EF_SIZE   304 /* size in bytes */
+
+#define EF_R0     LOONGARCH64_EF_R0
+#define EF_R1     LOONGARCH64_EF_R1
+#define EF_R2     LOONGARCH64_EF_R2
+#define EF_R3     LOONGARCH64_EF_R3
+#define EF_R4     LOONGARCH64_EF_R4
+#define EF_R5     LOONGARCH64_EF_R5
+#define EF_R6     LOONGARCH64_EF_R6
+#define EF_R7     LOONGARCH64_EF_R7
+#define EF_R8     LOONGARCH64_EF_R8
+#define EF_R9     LOONGARCH64_EF_R9
+#define EF_R10      LOONGARCH64_EF_R10
+#define EF_R11      LOONGARCH64_EF_R11
+#define EF_R12      LOONGARCH64_EF_R12
+#define EF_R13      LOONGARCH64_EF_R13
+#define EF_R14      LOONGARCH64_EF_R14
+#define EF_R15      LOONGARCH64_EF_R15
+#define EF_R16      LOONGARCH64_EF_R16
+#define EF_R17      LOONGARCH64_EF_R17
+#define EF_R18      LOONGARCH64_EF_R18
+#define EF_R19      LOONGARCH64_EF_R19
+#define EF_R20      LOONGARCH64_EF_R20
+#define EF_R21      LOONGARCH64_EF_R21
+#define EF_R22      LOONGARCH64_EF_R22
+#define EF_R23      LOONGARCH64_EF_R23
+#define EF_R24      LOONGARCH64_EF_R24
+#define EF_R25      LOONGARCH64_EF_R25
+#define EF_R26      LOONGARCH64_EF_R26
+#define EF_R27      LOONGARCH64_EF_R27
+#define EF_R28      LOONGARCH64_EF_R28
diff --git a/arch/loongarch64/bits/resource.h b/arch/loongarch64/bits/resource.h
new file mode 100644
index 00000000..da983617
--- /dev/null
+++ b/arch/loongarch64/bits/resource.h
@@ -0,0 +1,5 @@
+#define RLIMIT_NOFILE  7 /* num of file limit, able to open file */
+#define RLIMIT_AS      9 /* address space limit */
+#define RLIMIT_RSS     5 /* max resident set size */
+#define RLIMIT_NPROC   6 /* max number of processes */
+#define RLIMIT_MEMLOCK 8 /* max locked-in-memory address space */
diff --git a/arch/loongarch64/bits/setjmp.h b/arch/loongarch64/bits/setjmp.h
new file mode 100644
index 00000000..f4a7f8a3
--- /dev/null
+++ b/arch/loongarch64/bits/setjmp.h
@@ -0,0 +1 @@
+typedef unsigned long long __jmp_buf[22];
diff --git a/arch/loongarch64/bits/signal.h b/arch/loongarch64/bits/signal.h
new file mode 100644
index 00000000..318551a7
--- /dev/null
+++ b/arch/loongarch64/bits/signal.h
@@ -0,0 +1,144 @@
+#if defined(_POSIX_SOURCE) || defined(_POSIX_C_SOURCE) \
+ || defined(_XOPEN_SOURCE) || defined(_GNU_SOURCE) || defined(_BSD_SOURCE)
+
+#if defined(_XOPEN_SOURCE) || defined(_GNU_SOURCE) || defined(_BSD_SOURCE)
+#define MINSIGSTKSZ 8192
+#define SIGSTKSZ (MINSIGSTKSZ + 32768)
+#endif
+
+#define ARCH_MIN_TASKALIGN	32
+#define FPU_REG_WIDTH		256
+#define FPU_ALIGN		__attribute__((aligned(32)))
+
+#if defined(_GNU_SOURCE) || defined(_BSD_SOURCE)
+typedef unsigned long greg_t, gregset_t[32];
+
+struct sigcontext {
+	unsigned long   sc_pc;
+	unsigned long   sc_regs[32];
+	unsigned int    sc_flags;
+	unsigned int    sc_fcsr;
+	unsigned int    sc_vcsr;
+	unsigned long   sc_fcc;
+	unsigned long   sc_scr[4];
+	union {
+		unsigned int		val32[FPU_REG_WIDTH / 32];
+		unsigned long long	val64[FPU_REG_WIDTH / 64];
+	} sc_fpregs[32] FPU_ALIGN;
+	unsigned char	sc_reserved[4096] __attribute__((__aligned__(16)));
+};
+
+typedef struct {
+	unsigned long   pc;
+	unsigned long   gregs[32];
+	unsigned int    flags;
+	unsigned int    fcsr;
+	unsigned int    vcsr;
+	unsigned long   fcc;
+	unsigned long   scr[4];
+	union {
+                unsigned int            val32[FPU_REG_WIDTH / 32];
+                unsigned long long      val64[FPU_REG_WIDTH / 64];
+        } fpregs[32] FPU_ALIGN;
+	unsigned char   reserved[4096] __attribute__((__aligned__(16)));
+} mcontext_t;
+
+#else
+typedef struct {
+	unsigned long __mc1[32];
+	union {
+                unsigned int            val32[FPU_REG_WIDTH / 32];
+                unsigned long long      val64[FPU_REG_WIDTH / 64];
+        } _mc2[32] FPU_ALIGN;
+	unsigned int __mc3[3];
+	unsigned long __mc4[2];
+	unsigned long __mc5[4];
+	unsigned char reserved[4096] __attribute__((__aligned__(16)));
+} mcontext_t;
+
+#endif
+
+struct sigaltstack {
+	void *ss_sp;
+	int ss_flags;
+	size_t ss_size;
+};
+
+typedef struct __ucontext
+{
+	unsigned long  __uc_flags;
+	struct __ucontext *uc_link;
+	stack_t            uc_stack;
+	mcontext_t uc_mcontext;
+	sigset_t           uc_sigmask;
+} ucontext_t;
+
+
+#define SA_NOCLDSTOP  1          /* Don't send SIGCHLD when children stop.  */
+#define SA_NOCLDWAIT  2          /* Don't create zombie on child death.  */
+#define SA_SIGINFO    4          /* Invoke signal-catching function with
+                                    three arguments instead of one.  */
+#define SA_ONSTACK   0x08000000 /* Use signal stack by using `sa_restorer'. */
+#define SA_RESTART   0x10000000 /* Restart syscall on signal return.  */
+#define SA_NODEFER   0x40000000 /* Don't automatically block the signal when
+                                    its handler is being executed.  */
+#define SA_RESETHAND 0x80000000 /* Reset to SIG_DFL on entry to handler.  */
+#define SA_RESTORER  0x04000000
+
+#undef SIG_BLOCK
+#undef SIG_UNBLOCK
+#undef SIG_SETMASK
+#define SIG_BLOCK     0
+#define SIG_UNBLOCK   1
+#define SIG_SETMASK   2
+
+#undef SI_ASYNCIO
+#undef SI_MESGQ
+#undef SI_TIMER
+#define SI_ASYNCIO (-4)
+#define SI_MESGQ (-3)
+#define SI_TIMER (-2)
+
+
+#endif
+
+#define SIGHUP           1
+#define SIGINT           2
+#define SIGQUIT          3
+#define SIGILL           4
+#define SIGTRAP          5
+#define SIGABRT          6
+#define SIGIOT           6
+#define SIGBUS           7
+#define SIGFPE           8
+#define SIGKILL          9
+#define SIGUSR1         10
+#define SIGSEGV         11
+#define SIGUSR2         12
+#define SIGPIPE         13
+#define SIGALRM         14
+#define SIGTERM         15
+#define SIGSTKFLT       16
+#define SIGCHLD         17
+#define SIGCONT         18
+#define SIGSTOP         19
+#define SIGTSTP         20
+#define SIGTTIN         21
+#define SIGTTOU         22
+#define SIGURG          23
+#define SIGXCPU         24
+#define SIGXFSZ         25
+#define SIGVTALRM       26
+#define SIGPROF         27
+#define SIGWINCH        28
+#define SIGIO           29
+#define SIGPOLL         SIGIO
+/*
+#define SIGLOST         29
+*/
+#define SIGPWR          30
+#define SIGSYS          31
+
+#define SIGUNUSED SIGSYS
+
+#define _NSIG 128
diff --git a/arch/loongarch64/bits/stat.h b/arch/loongarch64/bits/stat.h
new file mode 100644
index 00000000..b620e142
--- /dev/null
+++ b/arch/loongarch64/bits/stat.h
@@ -0,0 +1,20 @@
+struct stat {
+	dev_t st_dev;
+	int __pad1[3];
+	ino_t st_ino;
+	mode_t st_mode;
+	nlink_t st_nlink;
+	uid_t st_uid;
+	gid_t st_gid;
+	dev_t st_rdev;
+	unsigned int __pad2[2];
+	off_t st_size;
+	int __pad3;
+	struct timespec st_atim;
+	struct timespec st_mtim;
+	struct timespec st_ctim;
+	blksize_t st_blksize;
+	unsigned int __pad4;
+	blkcnt_t st_blocks;
+	int __pad5[14];
+};
diff --git a/arch/loongarch64/bits/statfs.h b/arch/loongarch64/bits/statfs.h
new file mode 100644
index 00000000..389954ae
--- /dev/null
+++ b/arch/loongarch64/bits/statfs.h
@@ -0,0 +1,6 @@
+struct statfs {
+	long f_type, f_bsize;
+	unsigned long f_blocks, f_bfree, f_bavail, f_files, f_ffree;
+	fsid_t f_fsid;
+	long f_namelen, f_frsize, f_flags, f_spare[4];
+};
diff --git a/arch/loongarch64/bits/stdint.h b/arch/loongarch64/bits/stdint.h
new file mode 100644
index 00000000..1bb147f2
--- /dev/null
+++ b/arch/loongarch64/bits/stdint.h
@@ -0,0 +1,20 @@
+typedef int32_t int_fast16_t;
+typedef int32_t int_fast32_t;
+typedef uint32_t uint_fast16_t;
+typedef uint32_t uint_fast32_t;
+
+#define INT_FAST16_MIN  INT32_MIN
+#define INT_FAST32_MIN  INT32_MIN
+
+#define INT_FAST16_MAX  INT32_MAX
+#define INT_FAST32_MAX  INT32_MAX
+
+#define UINT_FAST16_MAX UINT32_MAX
+#define UINT_FAST32_MAX UINT32_MAX
+
+#define INTPTR_MIN      INT64_MIN
+#define INTPTR_MAX      INT64_MAX
+#define UINTPTR_MAX     UINT64_MAX
+#define PTRDIFF_MIN     INT64_MIN
+#define PTRDIFF_MAX     INT64_MAX
+#define SIZE_MAX        UINT64_MAX
diff --git a/arch/loongarch64/bits/syscall.h.in b/arch/loongarch64/bits/syscall.h.in
new file mode 100644
index 00000000..74bfd799
--- /dev/null
+++ b/arch/loongarch64/bits/syscall.h.in
@@ -0,0 +1,291 @@
+#define __NR_io_setup                   0
+#define __NR_io_destroy                 1
+#define __NR_io_submit                  2
+#define __NR_io_cancel                  3
+#define __NR_io_getevents               4
+#define __NR_setxattr                   5
+#define __NR_lsetxattr                  6
+#define __NR_fsetxattr                  7
+#define __NR_getxattr                   8
+#define __NR_lgetxattr                  9
+#define __NR_fgetxattr                  10
+#define __NR_listxattr                  11
+#define __NR_llistxattr                 12
+#define __NR_flistxattr                 13
+#define __NR_removexattr                14
+#define __NR_lremovexattr               15
+#define __NR_fremovexattr               16
+#define __NR_getcwd                     17
+#define __NR_lookup_dcookie             18
+#define __NR_eventfd2                   19
+#define __NR_epoll_create1              20
+#define __NR_epoll_ctl                  21
+#define __NR_epoll_pwait                22
+#define __NR_dup                        23
+#define __NR_dup3                       24
+#define __NR3264_fcntl                  25
+#define __NR_inotify_init1              26
+#define __NR_inotify_add_watch          27
+#define __NR_inotify_rm_watch           28
+#define __NR_ioctl                      29
+#define __NR_ioprio_set                 30
+#define __NR_ioprio_get                 31
+#define __NR_flock                      32
+#define __NR_mknodat                    33
+#define __NR_mkdirat                    34
+#define __NR_unlinkat                   35
+#define __NR_symlinkat                  36
+#define __NR_linkat                     37
+#define __NR_umount2                    39
+#define __NR_mount                      40
+#define __NR_pivot_root                 41
+#define __NR_nfsservctl                 42
+#define __NR3264_statfs                 43
+#define __NR3264_fstatfs                44
+#define __NR3264_truncate               45
+#define __NR3264_ftruncate              46
+#define __NR_fallocate                  47
+#define __NR_faccessat                  48
+#define __NR_faccessat2                 48
+#define __NR_chdir                      49
+#define __NR_fchdir                     50
+#define __NR_chroot                     51
+#define __NR_fchmod                     52
+#define __NR_fchmodat                   53
+#define __NR_fchownat                   54
+#define __NR_fchown                     55
+#define __NR_openat                     56
+#define __NR_close                      57
+#define __NR_vhangup                    58
+#define __NR_pipe2                      59
+#define __NR_quotactl                   60
+#define __NR_getdents64                 61
+#define __NR3264_lseek                  62
+#define __NR_read                       63
+#define __NR_write                      64
+#define __NR_readv                      65
+#define __NR_writev                     66
+#define __NR_pread64                    67
+#define __NR_pwrite64                   68
+#define __NR_preadv                     69
+#define __NR_pwritev                    70
+#define __NR3264_sendfile               71
+#define __NR_pselect6                   72
+#define __NR_ppoll                      73
+#define __NR_signalfd4                  74
+#define __NR_vmsplice                   75
+#define __NR_splice                     76
+#define __NR_tee                        77
+#define __NR_readlinkat                 78
+#define __NR3264_fstatat                79
+#define __NR3264_fstat                  80
+#define __NR_sync                       81
+#define __NR_fsync                      82
+#define __NR_fdatasync                  83
+#define __NR_sync_file_range            84
+#define __NR_timerfd_create             85
+#define __NR_timerfd_settime            86
+#define __NR_timerfd_gettime            87
+#define __NR_utimensat                  88
+#define __NR_acct                       89
+#define __NR_capget                     90
+#define __NR_capset                     91
+#define __NR_personality                92
+#define __NR_exit                       93
+#define __NR_exit_group                 94
+#define __NR_waitid                     95
+#define __NR_set_tid_address            96
+#define __NR_unshare                    97
+#define __NR_futex                      98
+#define __NR_set_robust_list            99
+#define __NR_get_robust_list            100
+#define __NR_nanosleep                  101
+#define __NR_getitimer                  102
+#define __NR_setitimer                  103
+#define __NR_kexec_load                 104
+#define __NR_init_module                105
+#define __NR_delete_module              106
+#define __NR_timer_create               107
+#define __NR_timer_gettime              108
+#define __NR_timer_getoverrun           109
+#define __NR_timer_settime              110
+#define __NR_timer_delete               111
+#define __NR_clock_settime              112
+#define __NR_clock_gettime              113
+#define __NR_clock_getres               114
+#define __NR_clock_nanosleep            115
+#define __NR_syslog                     116
+#define __NR_ptrace                     117
+#define __NR_sched_setparam             118
+#define __NR_sched_setscheduler         119
+#define __NR_sched_getscheduler         120
+#define __NR_sched_getparam             121
+#define __NR_sched_setaffinity          122
+#define __NR_sched_getaffinity          123
+#define __NR_sched_yield                124
+#define __NR_sched_get_priority_max     125
+#define __NR_sched_get_priority_min     126
+#define __NR_sched_rr_get_interval      127
+#define __NR_restart_syscall            128
+#define __NR_kill                       129
+#define __NR_tkill                      130
+#define __NR_tgkill                     131
+#define __NR_sigaltstack                132
+#define __NR_rt_sigsuspend              133
+#define __NR_rt_sigaction               134
+#define __NR_rt_sigprocmask             135
+#define __NR_rt_sigpending              136
+#define __NR_rt_sigtimedwait            137
+#define __NR_rt_sigqueueinfo            138
+#define __NR_rt_sigreturn               139
+#define __NR_setpriority                140
+#define __NR_getpriority                141
+#define __NR_reboot                     142
+#define __NR_setregid                   143
+#define __NR_setgid                     144
+#define __NR_setreuid                   145
+#define __NR_setuid                     146
+#define __NR_setresuid                  147
+#define __NR_getresuid                  148
+#define __NR_setresgid                  149
+#define __NR_getresgid                  150
+#define __NR_setfsuid                   151
+#define __NR_setfsgid                   152
+#define __NR_times                      153
+#define __NR_setpgid                    154
+#define __NR_getpgid                    155
+#define __NR_getsid                     156
+#define __NR_setsid                     157
+#define __NR_getgroups                  158
+#define __NR_setgroups                  159
+#define __NR_uname                      160
+#define __NR_sethostname                161
+#define __NR_setdomainname              162
+#define __NR_getrlimit                  163
+#define __NR_setrlimit                  164
+#define __NR_getrusage                  165
+#define __NR_umask                      166
+#define __NR_prctl                      167
+#define __NR_getcpu                     168
+#define __NR_gettimeofday               169
+#define __NR_settimeofday               170
+#define __NR_adjtimex                   171
+#define __NR_getpid                     172
+#define __NR_getppid                    173
+#define __NR_getuid                     174
+#define __NR_geteuid                    175
+#define __NR_getgid                     176
+#define __NR_getegid                    177
+#define __NR_gettid                     178
+#define __NR_sysinfo                    179
+#define __NR_mq_open                    180
+#define __NR_mq_unlink                  181
+#define __NR_mq_timedsend               182
+#define __NR_mq_timedreceive            183
+#define __NR_mq_notify                  184
+#define __NR_mq_getsetattr              185
+#define __NR_msgget                     186
+#define __NR_msgctl                     187
+#define __NR_msgrcv                     188
+#define __NR_msgsnd                     189
+#define __NR_semget                     190
+#define __NR_semctl                     191
+#define __NR_semtimedop                 192
+#define __NR_semop                      193
+#define __NR_shmget                     194
+#define __NR_shmctl                     195
+#define __NR_shmat                      196
+#define __NR_shmdt                      197
+#define __NR_socket                     198
+#define __NR_socketpair                 199
+#define __NR_bind                       200
+#define __NR_listen                     201
+#define __NR_accept                     202
+#define __NR_connect                    203
+#define __NR_getsockname                204
+#define __NR_getpeername                205
+#define __NR_sendto                     206
+#define __NR_recvfrom                   207
+#define __NR_setsockopt                 208
+#define __NR_getsockopt                 209
+#define __NR_shutdown                   210
+#define __NR_sendmsg                    211
+#define __NR_recvmsg                    212
+#define __NR_readahead                  213
+#define __NR_brk                        214
+#define __NR_munmap                     215
+#define __NR_mremap                     216
+#define __NR_add_key                    217
+#define __NR_request_key                218
+#define __NR_keyctl                     219
+#define __NR_clone                      220
+#define __NR_execve                     221
+#define __NR3264_mmap                   222
+#define __NR3264_fadvise64              223
+#define __NR_swapon                     224
+#define __NR_swapoff                    225
+#define __NR_mprotect                   226
+#define __NR_msync                      227
+#define __NR_mlock                      228
+#define __NR_munlock                    229
+#define __NR_mlockall                   230
+#define __NR_munlockall                 231
+#define __NR_mincore                    232
+#define __NR_madvise                    233
+#define __NR_remap_file_pages           234
+#define __NR_mbind                      235
+#define __NR_get_mempolicy              236
+#define __NR_set_mempolicy              237
+#define __NR_migrate_pages              238
+#define __NR_move_pages                 239
+#define __NR_rt_tgsigqueueinfo          240
+#define __NR_perf_event_open            241
+#define __NR_accept4                    242
+#define __NR_recvmmsg                   243
+#define __NR_arch_specific_syscall      244
+#define __NR_wait4                      260
+#define __NR_prlimit64                  261
+#define __NR_fanotify_init              262
+#define __NR_fanotify_mark              263
+#define __NR_name_to_handle_at          264
+#define __NR_open_by_handle_at          265
+#define __NR_clock_adjtime              266
+#define __NR_syncfs                     267
+#define __NR_setns                      268
+#define __NR_sendmmsg                   269
+#define __NR_process_vm_readv           270
+#define __NR_process_vm_writev          271
+#define __NR_kcmp                       272
+#define __NR_finit_module               273
+#define __NR_sched_setattr              274
+#define __NR_sched_getattr              275
+#define __NR_renameat2                  276
+#define __NR_seccomp                    277
+#define __NR_getrandom                  278
+#define __NR_memfd_create               279
+#define __NR_bpf                        280
+#define __NR_execveat                   281
+#define __NR_userfaultfd                282
+#define __NR_membarrier                 283
+#define __NR_mlock2                     284
+#define __NR_copy_file_range            285
+#define __NR_preadv2                    286
+#define __NR_pwritev2                   287
+#define __NR_pkey_mprotect              288
+#define __NR_pkey_alloc                 289
+#define __NR_pkey_free                  290
+#define __NR_statx                      291
+#define __NR_io_pgetevents              292
+#define __NR_rseq                       293
+#define __NR_syscalls                   294
+#define __NR_fcntl                      __NR3264_fcntl
+#define __NR_statfs                     __NR3264_statfs
+#define __NR_fstatfs                    __NR3264_fstatfs
+#define __NR_truncate                   __NR3264_truncate
+#define __NR_ftruncate                  __NR3264_ftruncate
+#define __NR_lseek                      __NR3264_lseek
+#define __NR_sendfile                   __NR3264_sendfile
+#define __NR_newfstatat                 __NR3264_fstatat
+#define __NR_fstat                      __NR3264_fstat
+#define __NR_mmap                       __NR3264_mmap
+#define __NR_fadvise64                  __NR3264_fadvise64
diff --git a/arch/loongarch64/bits/user.h b/arch/loongarch64/bits/user.h
new file mode 100644
index 00000000..4d4cd534
--- /dev/null
+++ b/arch/loongarch64/bits/user.h
@@ -0,0 +1,5 @@
+#define ELF_NGREG	45
+#define ELF_NFPREG	33
+
+typedef unsigned long elf_greg_t, elf_gregset_t[ELF_NGREG];
+typedef double elf_fpreg_t, elf_fpregset_t[ELF_NFPREG];
diff --git a/arch/loongarch64/crt_arch.h b/arch/loongarch64/crt_arch.h
new file mode 100644
index 00000000..3db6aad5
--- /dev/null
+++ b/arch/loongarch64/crt_arch.h
@@ -0,0 +1,23 @@
+__asm__(
+".text \n"
+".global _" START "\n"
+".global " START "\n"
+".global " START "_data\n"
+".type   _" START ", @function\n"
+".type   " START ", @function\n"
+".type   " START "_data, @function\n"
+"_" START ":\n"
+"" START ":\n"
+".align 8 \n"
+"	add.w $fp, $r0,$r0 \n"
+"	bl 1f \n"
+"" START "_data: \n"
+".weak _DYNAMIC \n"
+".hidden _DYNAMIC \n"
+"1:	or $a0, $sp, $zero \n"
+"	la.local $a1, _DYNAMIC \n"
+"	addi.w $r19, $r0, -16 \n"
+"	and $sp, $sp, $r19 \n"
+"	la.local $t0," START "_c \n"
+"	jirl $t1,$t0,0 \n"
+);
diff --git a/arch/loongarch64/ksigaction.h b/arch/loongarch64/ksigaction.h
new file mode 100644
index 00000000..0d352e8c
--- /dev/null
+++ b/arch/loongarch64/ksigaction.h
@@ -0,0 +1,13 @@
+#include <features.h>
+
+/* This is the structure used for the rt_sigaction syscall on most archs,
+ * but it can be overridden by a file with the same name in the top-level
+ * arch dir for a given arch, if necessary. */
+struct k_sigaction {
+	void (*handler)(int);
+	unsigned long flags;
+	unsigned long mask[2];
+	void (*restorer)();
+};
+
+hidden void __restore(), __restore_rt();
diff --git a/arch/loongarch64/kstat.h b/arch/loongarch64/kstat.h
new file mode 100644
index 00000000..f66ed2e9
--- /dev/null
+++ b/arch/loongarch64/kstat.h
@@ -0,0 +1,22 @@
+struct kstat {
+    unsigned long   st_dev;     /* Device.  */
+    unsigned long   st_ino;     /* File serial number.  */
+    unsigned int    st_mode;    /* File mode.  */
+    unsigned int    st_nlink;   /* Link count.  */
+    unsigned int    st_uid;     /* User ID of the file's owner.  */
+    unsigned int    st_gid;     /* Group ID of the file's group. */
+    unsigned long   st_rdev;    /* Device number, if device.  */
+    unsigned long   __pad1;
+    long        st_size;    /* Size of file, in bytes.  */
+    int     st_blksize; /* Optimal block size for I/O.  */
+    int     __pad2;
+    long        st_blocks;  /* Number 512-byte blocks allocated. */
+    long        st_atime_sec;   /* Time of last access.  */
+    unsigned long   st_atime_nsec;
+    long        st_mtime_sec;   /* Time of last modification.  */
+    unsigned long   st_mtime_nsec;
+    long        st_ctime_sec;   /* Time of last status change.  */
+    unsigned long   st_ctime_nsec;
+    unsigned int    __unused4;
+    unsigned int    __unused5;
+};
diff --git a/arch/loongarch64/pthread_arch.h b/arch/loongarch64/pthread_arch.h
new file mode 100644
index 00000000..27f50e4c
--- /dev/null
+++ b/arch/loongarch64/pthread_arch.h
@@ -0,0 +1,13 @@
+static inline uintptr_t __get_tp()
+{
+	uintptr_t tp;
+	__asm__ ("or %0, $tp, $zero" : "=r" (tp) );
+	return tp;
+}
+
+#define TLS_ABOVE_TP
+#define GAP_ABOVE_TP 0
+
+#define DTP_OFFSET 0
+
+#define MC_PC pc
diff --git a/arch/loongarch64/reloc.h b/arch/loongarch64/reloc.h
new file mode 100644
index 00000000..6e2b67e9
--- /dev/null
+++ b/arch/loongarch64/reloc.h
@@ -0,0 +1,43 @@
+#ifndef __RELOC_H__
+#define __RELOC_H__
+
+#define _GNU_SOURCE
+#include <endian.h>
+
+#ifdef __loongarch64_soft_float
+#define FP_SUFFIX "-sf"
+#else
+#define FP_SUFFIX ""
+#endif
+
+#define LDSO_ARCH "loongarch64"  FP_SUFFIX
+
+#define TPOFF_K (0x0)
+
+//#define REL_SYM_OR_REL  4611  
+#define REL_PLT         R_LOONGARCH_JUMP_SLOT
+#define REL_COPY        R_LOONGARCH_COPY
+#define REL_DTPMOD      R_LOONGARCH_TLS_DTPMOD64
+#define REL_DTPOFF      R_LOONGARCH_TLS_DTPREL64
+#define REL_TPOFF       R_LOONGARCH_TLS_TPREL64
+#define REL_RELATIVE    R_LOONGARCH_RELATIVE
+#define REL_SYMBOLIC    R_LOONGARCH_64
+
+//#undef R_TYPE
+//#undef R_SYM
+//#undef R_INFO
+//#define R_TYPE(x) (be64toh(x)&0x7fffffff)
+//#define R_SYM(x) (be32toh(be64toh(x)>>32))
+//#define R_INFO(s,t) (htobe64((uint64_t)htobe32(s)<<32 | (uint64_t)t))
+
+#define CRTJMP(pc,sp) __asm__ __volatile__( \
+	"move $sp,%1 ; jr %0" : : "r"(pc), "r"(sp) : "memory" )
+
+#define GETFUNCSYM(fp, sym, got) __asm__ ( \
+	".hidden " #sym "\n" \
+	".align 8 \n" \
+	"	la.local $t1, "#sym" \n" \
+	"	or %0, $t1, $zero \n" \
+	: "=r"(*(fp)) : : "memory" )
+
+#endif
diff --git a/arch/loongarch64/syscall_arch.h b/arch/loongarch64/syscall_arch.h
new file mode 100644
index 00000000..5b44089f
--- /dev/null
+++ b/arch/loongarch64/syscall_arch.h
@@ -0,0 +1,121 @@
+#define IPC_64 0x0
+
+#define __SYSCALL_LL_E(x) (x)
+#define __SYSCALL_LL_O(x) (x)
+
+#define SYSCALL_CLOBBERLIST \
+	"$t0", "$t1", "$t2", "$t3", \
+	"$t4", "$t5", "$t6", "$t7", "$t8", "memory"
+
+static inline long __syscall0(long n)
+{
+	register long a0 __asm__("$a0");
+	register long a7 __asm__("$a7") = n;
+
+	__asm__ __volatile__ (
+		"syscall 0"
+		: "+&r"(a0)
+		: "r"(a7)
+		: SYSCALL_CLOBBERLIST);
+	return a0;
+}
+
+static inline long __syscall1(long n, long a)
+{
+	register long a0 __asm__("$a0") = a;
+	register long a7 __asm__("$a7") = n;
+
+	__asm__ __volatile__ (
+		"syscall 0"
+		: "+&r"(a0)
+		: "r"(a7)
+		: SYSCALL_CLOBBERLIST);
+	return a0;
+}
+
+static inline long __syscall2(long n, long a, long b)
+{
+	register long a0 __asm__("$a0") = a;
+	register long a1 __asm__("$a1") = b;
+	register long a7 __asm__("$a7") = n;
+
+	__asm__ __volatile__ (
+		"syscall 0"
+		: "+&r"(a0)
+	        : "r"(a7), "r"(a1)
+		: SYSCALL_CLOBBERLIST);
+	return a0;
+}
+
+static inline long __syscall3(long n, long a, long b, long c)
+{
+	register long a0 __asm__("$a0") = a;
+	register long a1 __asm__("$a1") = b;
+	register long a2 __asm__("$a2") = c;
+	register long a7 __asm__("$a7") = n;
+
+	__asm__ __volatile__ (
+		"syscall 0"
+		: "+&r"(a0)
+	        : "r"(a7), "r"(a1), "r"(a2)
+		: SYSCALL_CLOBBERLIST);
+	return a0;
+}
+
+static inline long __syscall4(long n, long a, long b, long c, long d)
+{
+	register long a0 __asm__("$a0") = a;
+	register long a1 __asm__("$a1") = b;
+	register long a2 __asm__("$a2") = c;
+	register long a3 __asm__("$a3") = d;
+	register long a7 __asm__("$a7") = n;
+
+	__asm__ __volatile__ (
+		"syscall 0"
+		: "+&r"(a0)
+	        : "r"(a7), "r"(a1), "r"(a2), "r"(a3)
+		: SYSCALL_CLOBBERLIST);
+	return a0;
+}
+
+static inline long __syscall5(long n, long a, long b, long c, long d, long e)
+{
+	register long a0 __asm__("$a0") = a;
+	register long a1 __asm__("$a1") = b;
+	register long a2 __asm__("$a2") = c;
+	register long a3 __asm__("$a3") = d;
+	register long a4 __asm__("$a4") = e;
+	register long a7 __asm__("$a7") = n;
+
+	__asm__ __volatile__ (
+		"syscall 0"
+		: "+&r"(a0)
+	        : "r"(a7), "r"(a1), "r"(a2), "r"(a3), "r"(a4)
+		: SYSCALL_CLOBBERLIST);
+	return a0;
+}
+
+static inline long __syscall6(long n, long a, long b, long c, long d, long e, long f)
+{
+	register long a0 __asm__("$a0") = a;
+	register long a1 __asm__("$a1") = b;
+	register long a2 __asm__("$a2") = c;
+	register long a3 __asm__("$a3") = d;
+	register long a4 __asm__("$a4") = e;
+	register long a5 __asm__("$a5") = f;
+	register long a7 __asm__("$a7") = n;
+
+	__asm__ __volatile__ (
+		"syscall 0"
+		: "+&r"(a0)
+	        : "r"(a7), "r"(a1), "r"(a2), "r"(a3), "r"(a4), "r"(a5)
+		: SYSCALL_CLOBBERLIST);
+	return a0;
+}
+
+#define VDSO_USEFUL
+#define VDSO_CGT_SYM "__vdso_clock_gettime"
+#define VDSO_CGT_VER "LINUX_2.6"
+
+#define SO_SNDTIMEO_OLD 21
+#define SO_RCVTIMEO_OLD 20
diff --git a/configure b/configure
index a5231a0e..54b7aa2b 100755
--- a/configure
+++ b/configure
@@ -338,6 +338,7 @@ powerpc*|ppc*) ARCH=powerpc ;;
 riscv64*) ARCH=riscv64 ;;
 sh[1-9bel-]*|sh|superh*) ARCH=sh ;;
 s390x*) ARCH=s390x ;;
+loongarch64*) ARCH=loongarch64 ;;
 unknown) fail "$0: unable to detect target arch; try $0 --target=..." ;;
 *) fail "$0: unknown or unsupported target \"$target\"" ;;
 esac
diff --git a/crt/loongarch64/crti.s b/crt/loongarch64/crti.s
new file mode 100644
index 00000000..77dc262e
--- /dev/null
+++ b/crt/loongarch64/crti.s
@@ -0,0 +1,15 @@
+.section .init
+.global _init
+.align 3
+_init:
+	addi.d	$r3,$r3,-32
+	st.d	$r31,$r3,16
+	st.d	$r1,$r3,24
+
+.section .fini
+.global _fini
+.align 3
+_fini:
+	addi.d	$r3,$r3,-32
+	st.d	$r31,$r3,16
+	st.d	$r1,$r3,24
diff --git a/crt/loongarch64/crtn.s b/crt/loongarch64/crtn.s
new file mode 100644
index 00000000..12c27c66
--- /dev/null
+++ b/crt/loongarch64/crtn.s
@@ -0,0 +1,12 @@
+.section .init
+	ld.d	$r31,$r3,16
+	ld.d	$r1,$r3,24
+	addi.d	$r3,$r3,32
+	jirl	$r0,$r1,0
+
+
+.section .fini
+	ld.d	$r31,$r3,16
+	ld.d	$r1,$r3,24
+	addi.d	$r3,$r3,32
+	jirl	$r0,$r1,0
diff --git a/include/elf.h b/include/elf.h
index 5170f3e2..47a86615 100644
--- a/include/elf.h
+++ b/include/elf.h
@@ -696,6 +696,10 @@ typedef struct {
 #define NT_MIPS_FP_MODE	0x801
 #define NT_MIPS_MSA	0x802
 #define NT_VERSION	1
+#define NT_LOONGARCH_CPUCFG     0x900           /* Loongarch CPU config registers */
+#define NT_LOONGARCH_LBT        0x901           /* Loongarch Loongson Binary Translation registers */
+#define NT_LOONGARCH_LSX        0x902           /* Loongarch Loongson SIMD Extension registers */
+#define NT_LOONGARCH_LASX       0x903           /* Loongarch Loongson Advanced SIMD Extension registers */
 
 
 
@@ -3287,6 +3291,67 @@ enum
 #define R_RISCV_SET32           56
 #define R_RISCV_32_PCREL        57
 
+/* LoongISA ELF Flags */
+#define EM_LOONGARCH  258
+#define EF_LOONGARCH_ABI             0x0003
+#define EF_LOONGARCH_ABI_LP64        0x0003
+#define EF_LOONGARCH_ABI_LPX32       0x0002
+#define EF_LOONGARCH_ABI_LP32        0x0001
+
+/* Loongarch specific dynamic relocations. */
+#define R_LOONGARCH_NONE                        0
+#define R_LOONGARCH_32                          1
+#define R_LOONGARCH_64                          2
+#define R_LOONGARCH_RELATIVE                    3
+#define R_LOONGARCH_COPY                        4
+#define R_LOONGARCH_JUMP_SLOT                   5
+#define R_LOONGARCH_TLS_DTPMOD32                6
+#define R_LOONGARCH_TLS_DTPMOD64                7
+#define R_LOONGARCH_TLS_DTPREL32                8
+#define R_LOONGARCH_TLS_DTPREL64                9
+#define R_LOONGARCH_TLS_TPREL32                 10
+#define R_LOONGARCH_TLS_TPREL64                 11
+#define R_LOONGARCH_IRELATIVE                   12
+#define R_LOONGARCH_MARK_LA                     20
+#define R_LOONGARCH_MARK_PCREL                  21
+#define R_LOONGARCH_SOP_PUSH_PCREL              22
+#define R_LOONGARCH_SOP_PUSH_ABSOLUTE           23
+#define R_LOONGARCH_SOP_PUSH_DUP                24
+#define R_LOONGARCH_SOP_PUSH_GPREL              25
+#define R_LOONGARCH_SOP_PUSH_TLS_TPREL          26
+#define R_LOONGARCH_SOP_PUSH_TLS_GOT            27
+#define R_LOONGARCH_SOP_PUSH_TLS_GD             28
+#define R_LOONGARCH_SOP_PUSH_PLT_PCREL          29
+#define R_LOONGARCH_SOP_ASSERT                  30
+#define R_LOONGARCH_SOP_NOT                     31
+#define R_LOONGARCH_SOP_SUB                     32
+#define R_LOONGARCH_SOP_SL                      33
+#define R_LOONGARCH_SOP_SR                      34
+#define R_LOONGARCH_SOP_ADD                     35
+#define R_LOONGARCH_SOP_AND                     36
+#define R_LOONGARCH_SOP_IF_ELSE                 37
+#define R_LOONGARCH_SOP_POP_32_S_10_5           38
+#define R_LOONGARCH_SOP_POP_32_U_10_12          39
+#define R_LOONGARCH_SOP_POP_32_S_10_12          40
+#define R_LOONGARCH_SOP_POP_32_S_10_16          41
+#define R_LOONGARCH_SOP_POP_32_S_10_16_S2       42
+#define R_LOONGARCH_SOP_POP_32_S_5_20           43
+#define R_LOONGARCH_SOP_POP_32_S_0_5_10_16_S2   44
+#define R_LOONGARCH_SOP_POP_32_S_0_10_10_16_S2  45
+#define R_LOONGARCH_SOP_POP_32_U                46
+#define R_LOONGARCH_ADD8                        47
+#define R_LOONGARCH_ADD16                       48
+#define R_LOONGARCH_ADD24                       49
+#define R_LOONGARCH_ADD32                       50
+#define R_LOONGARCH_ADD64                       51
+#define R_LOONGARCH_SUB8                        52
+#define R_LOONGARCH_SUB16                       53
+#define R_LOONGARCH_SUB24                       54
+#define R_LOONGARCH_SUB32                       55
+#define R_LOONGARCH_SUB64                       56
+#define R_LOONGARCH_GNU_VTINHERIT               57
+#define R_LOONGARCH_GNU_VTENTRY                 58
+
 #ifdef __cplusplus
 }
 #endif
diff --git a/src/fenv/loongarch64/fenv-sf.c b/src/fenv/loongarch64/fenv-sf.c
new file mode 100644
index 00000000..6aa9b545
--- /dev/null
+++ b/src/fenv/loongarch64/fenv-sf.c
@@ -0,0 +1,3 @@
+#ifdef __loongarch64_soft_float
+#include "../fenv.c"
+#endif
diff --git a/src/fenv/loongarch64/fenv.S b/src/fenv/loongarch64/fenv.S
new file mode 100644
index 00000000..beb2868e
--- /dev/null
+++ b/src/fenv/loongarch64/fenv.S
@@ -0,0 +1,75 @@
+#ifndef __loongarch_soft_float
+
+.global	feclearexcept
+.type	feclearexcept,@function
+feclearexcept:
+	//andi	$a0, $a0, 0x1f0000 // la: exception bits in 16-20 bit of fcsr0.
+        li      $a1, 0x1f0000
+        and     $a0, $a0, $a1
+	movfcsr2gr $a1, $r0 // r0 is fpu control status register 0(fcsr0), r0 -> fcsr0, r1 -> fcsr1, r2 -> fcsr2, r3 - fcsr3
+	or	$a1, $a1, $a0
+	xor	$a1, $a1, $a0
+	movgr2fcsr $r0, $a1
+        li      $v0, 0
+	jr	$ra
+
+.global	feraiseexcept
+.type	feraiseexcept,@function
+feraiseexcept:
+	//andi	$a0, $a0, 0x1f0000
+        li      $a1, 0x1f0000
+        and     $a0, $a0, $a1
+	movfcsr2gr $a1, $r0
+	or	$a1, $a1, $a0
+	movgr2fcsr $r0, $a1
+        li      $v0, 0
+	jr	$ra
+
+.global	fetestexcept
+.type	fetestexcept,@function
+fetestexcept:
+	//andi	$a0, $a0, 0x1f0000
+        li      $a1, 0x1f0000
+        and     $a0, $a0, $a1
+	movfcsr2gr $a1, $r0
+        and     $v0, $a1, $a0
+	jr	$ra
+
+.global	fegetround
+.type	fegetround,@function
+fegetround:
+	movfcsr2gr $v0, $r0
+        andi    $v0, $v0, 0x300 // RM
+	jr	$ra
+
+.global	__fesetround
+.hidden __fesetround
+.type	__fesetround,@function
+__fesetround:
+	movfcsr2gr $a1, $r0
+	li	$a2, -769
+	and	$a1, $a1, $a2
+	or	$a1, $a1, $a0
+	movgr2fcsr $r0, $a1
+        li      $v0, 0
+	jr	$ra
+
+.global	fegetenv
+.type	fegetenv,@function
+fegetenv:
+	movfcsr2gr $a1, $r0
+	st.w	$a1, $a0, 0
+        li      $v0, 0
+	jr	$ra
+
+.global	fesetenv
+.type	fesetenv,@function
+fesetenv:
+	addi.d	$a1, $a0, 1
+	beq	$a1, $r0, 1f
+	ld.w	$a1, $a0, 0
+1:	movgr2fcsr $r0, $a1
+        li      $v0, 0
+	jr	$ra
+
+#endif
diff --git a/src/ldso/loongarch64/dlsym.s b/src/ldso/loongarch64/dlsym.s
new file mode 100644
index 00000000..2faa8ed3
--- /dev/null
+++ b/src/ldso/loongarch64/dlsym.s
@@ -0,0 +1,12 @@
+.global dlsym
+.hidden __dlsym
+.type   dlsym,@function
+dlsym:
+	move	$r6, $ra
+	la.global	$r16, __dlsym
+	addi.d 	$sp, $sp, -32
+	st.d	$ra, $sp, 24
+	jirl	$ra, $r16, 0
+	ld.d	$ra, $sp, 24
+	addi.d	$sp, $sp, 32
+	jr	$ra
diff --git a/src/setjmp/loongarch64/longjmp.S b/src/setjmp/loongarch64/longjmp.S
new file mode 100644
index 00000000..90529b8c
--- /dev/null
+++ b/src/setjmp/loongarch64/longjmp.S
@@ -0,0 +1,37 @@
+.global    _longjmp
+.global    longjmp
+.type    _longjmp,@function
+.type    longjmp,@function
+_longjmp:
+longjmp:
+	add.d   $t5, $a0, $zero
+	add.d   $v0, $a1, $zero
+	
+	bne     $v0, $zero, 1f
+	addi.d  $v0, $v0, 1
+
+1:
+	ld.d    $ra, $t5, 0
+	ld.d    $sp, $t5, 8
+	ld.d    $fp, $t5, 16
+	ld.d    $s0, $t5, 24
+	ld.d    $s1, $t5, 32
+	ld.d    $s2, $t5, 40
+	ld.d    $s3, $t5, 48
+	ld.d    $s4, $t5, 56
+	ld.d    $s5, $t5, 64
+	ld.d    $s6, $t5, 72
+	ld.d    $s7, $t5, 80
+	ld.d    $s8, $t5, 88
+#ifndef __loongarch64_soft_float
+	fld.d   $fs0, $t5, 96
+	fld.d   $fs1, $t5, 104
+	fld.d   $fs2, $t5, 112
+	fld.d   $fs3, $t5, 120
+	fld.d   $fs4, $t5, 128
+	fld.d   $fs5, $t5, 136
+	fld.d   $fs6, $t5, 144
+	fld.d   $fs7, $t5, 152
+#endif
+	jirl    $zero, $ra, 0
+
diff --git a/src/setjmp/loongarch64/setjmp.S b/src/setjmp/loongarch64/setjmp.S
new file mode 100644
index 00000000..83170dea
--- /dev/null
+++ b/src/setjmp/loongarch64/setjmp.S
@@ -0,0 +1,35 @@
+.global    __setjmp
+.global    _setjmp
+.global    setjmp
+.type    __setjmp,@function
+.type    _setjmp,@function
+.type    setjmp,@function
+__setjmp:
+_setjmp:
+setjmp:
+	st.d    $ra, $a0, 0
+	st.d    $sp, $a0, 8
+	
+	st.d    $fp, $a0, 16
+	st.d    $s0, $a0, 24
+	st.d    $s1, $a0, 32
+	st.d    $s2, $a0, 40
+	st.d    $s3, $a0, 48
+	st.d    $s4, $a0, 56
+	st.d    $s5, $a0, 64
+	st.d    $s6, $a0, 72
+	st.d    $s7, $a0, 80
+	st.d    $s8, $a0, 88
+#ifndef __loongarch64_soft_float
+	fst.d   $fs0, $a0, 96
+	fst.d   $fs1, $a0, 104
+	fst.d   $fs2, $a0, 112
+	fst.d   $fs3, $a0, 120
+	fst.d   $fs4, $a0, 128
+	fst.d   $fs5, $a0, 136
+	fst.d   $fs6, $a0, 144
+	fst.d   $fs7, $a0, 152
+#endif
+	xor     $v0, $v0, $v0
+	jirl    $zero, $ra, 0
+
diff --git a/src/signal/loongarch64/restore.s b/src/signal/loongarch64/restore.s
new file mode 100644
index 00000000..9bf015a0
--- /dev/null
+++ b/src/signal/loongarch64/restore.s
@@ -0,0 +1,10 @@
+.global	__restore_rt
+.global	__restore
+.hidden __restore_rt
+.hidden __restore
+.type	__restore_rt,@function
+.type	__restore,@function
+__restore_rt:
+__restore:
+	ori	$a7, $zero, 139
+	syscall	0
diff --git a/src/signal/loongarch64/sigsetjmp.s b/src/signal/loongarch64/sigsetjmp.s
new file mode 100644
index 00000000..e860c47b
--- /dev/null
+++ b/src/signal/loongarch64/sigsetjmp.s
@@ -0,0 +1,33 @@
+.global sigsetjmp
+.global __sigsetjmp
+.type   sigsetjmp,@function
+.type   __sigsetjmp,@function
+sigsetjmp:
+__sigsetjmp:
+        or $t5, $a0, $zero
+        or $t6, $a1, $zero
+
+        # comparing save mask with 0, if equals to 0 then
+        # sigsetjmp is equal to setjmp.
+        beq     $t6, $zero, 1f
+        st.d    $ra, $t5, 160
+        st.d    $s0, $t5, 168
+
+        # save base of got so that we can use it later
+        # once we return from 'longjmp'
+        la.global       $t8, setjmp
+        or      $s0, $a0, $zero
+        jirl    $ra, $t8, 0
+
+        or      $v1, $v0, $zero         # Return from 'setjmp' or 'longjmp'
+        ld.d    $ra, $t5, 160   # Restore ra of sigsetjmp
+        ld.d    $s0, $t5, 168   # Restore $s0 of sigsetjmp
+        or      $a0, $t5, $zero
+
+.hidden __sigsetjmp_tail
+        la.global       $t8, __sigsetjmp_tail
+        jr      $t8
+1:
+        la.global       $t8, setjmp
+        jr      $t8
+
diff --git a/src/thread/loongarch64/__set_thread_area.s b/src/thread/loongarch64/__set_thread_area.s
new file mode 100644
index 00000000..891ac076
--- /dev/null
+++ b/src/thread/loongarch64/__set_thread_area.s
@@ -0,0 +1,7 @@
+.global	__set_thread_area
+.type	__set_thread_area, @function
+__set_thread_area:
+	or	$tp, $a0, $zero
+	ori	$a0, $zero, 0
+	jirl	$zero, $ra, 0
+
diff --git a/src/thread/loongarch64/__unmapself.s b/src/thread/loongarch64/__unmapself.s
new file mode 100644
index 00000000..e0d2fcf6
--- /dev/null
+++ b/src/thread/loongarch64/__unmapself.s
@@ -0,0 +1,8 @@
+.global	__unmapself
+.type	__unmapself, @function
+__unmapself:
+	ori	$a7, $zero, 215
+	syscall	0				# call munmap
+	ori	$a0, $zero, 0
+	ori	$a7, $zero, 93
+	syscall	0				# call exit
diff --git a/src/thread/loongarch64/clone.s b/src/thread/loongarch64/clone.s
new file mode 100644
index 00000000..a3fd82ba
--- /dev/null
+++ b/src/thread/loongarch64/clone.s
@@ -0,0 +1,27 @@
+.global	__clone
+.hidden __clone
+.type	__clone,@function
+__clone:
+	# Save function pointer and argument pointer on new thread stack
+	addi.d	$a1, $a1, -16	# aligning stack to double word
+	st.d	$a0, $a1, 0		# save function pointer
+	st.d	$a3, $a1, 8		# save argument pointer
+
+	# Shuffle (fn,sp,fl,arg,ptid,tls,ctid) to (fl,sp,ptid,tls,ctid)
+	# sys_clone(u64 flags, u64 ustack_base, u64 parent_tidptr, u64 child_tidptr, u64 tls)
+	or	$a0, $a2, $zero
+	or	$a2, $a4, $zero
+	or	$a3, $a6, $zero
+	or	$a4, $a5, $zero
+	ori	$a7, $zero, 220
+	syscall 0				# call clone
+
+	beqz	$a0, 1f			# whether child process
+	jirl	$zero, $ra, 0	# parent process return
+1:
+	ld.d	$t8, $sp, 0     # function pointer
+	ld.d	$a0, $sp, 8     # argument pointer
+	jirl	$ra, $t8, 0     # call the user's function
+	ori	$a7, $zero, 93
+	syscall	0				# child process exit
+
diff --git a/src/thread/loongarch64/syscall_cp.s b/src/thread/loongarch64/syscall_cp.s
new file mode 100644
index 00000000..d833f625
--- /dev/null
+++ b/src/thread/loongarch64/syscall_cp.s
@@ -0,0 +1,34 @@
+.global	__cp_begin
+.hidden	__cp_begin
+.type	__cp_begin,@function
+.global	__cp_end
+.hidden	__cp_end
+.type	__cp_end,@function
+.global	__cp_cancel
+.hidden	__cp_cancel
+.type	__cp_cancel,@function
+.hidden	__cancel
+.global	__syscall_cp_asm
+.hidden	__syscall_cp_asm
+.type	__syscall_cp_asm,@function
+
+__syscall_cp_asm:
+__cp_begin:
+	ld.w	$a0, $a0, 0
+	bnez	$a0, __cp_cancel
+	or	$t8, $a1, $zero     # reserve system call number
+	or	$a0, $a2, $zero
+	or	$a1, $a3, $zero
+	or	$a2, $a4, $zero
+	or	$a3, $a5, $zero
+	or	$a4, $a6, $zero
+	or	$a5, $a7, $zero
+	ld.d	$a6, $sp, 0
+	or	$a7, $t8, $zero
+	syscall	0
+__cp_end:
+	jirl	$zero, $ra, 0
+__cp_cancel:
+	la.local $t8, __cancel
+	jirl	$zero, $t8, 0
+
diff --git a/src/unistd/loongarch64/pipe.s b/src/unistd/loongarch64/pipe.s
new file mode 100644
index 00000000..b7f5b7b4
--- /dev/null
+++ b/src/unistd/loongarch64/pipe.s
@@ -0,0 +1,12 @@
+.global pipe
+.type   pipe,@function
+pipe:
+	move	$a1, $r0
+	li	$a7, 59
+	syscall	0
+	li	$t0, -4096
+	bgeu	$t0, $v0, 1f
+	la.global	$t1, __syscall_ret
+	jr	$t1
+1:	move	$v0, $r0
+	jr	$ra
-- 
2.20.1


^ permalink raw reply	[flat|nested] 14+ messages in thread

* Re: Re: Re: [musl] Port the new architecture loongarch64 to musl
  2021-06-24 12:17       ` 翟小娟
@ 2021-06-24 12:47         ` 罗勇刚(Yonggang Luo)
  0 siblings, 0 replies; 14+ messages in thread
From: 罗勇刚(Yonggang Luo) @ 2021-06-24 12:47 UTC (permalink / raw)
  To: Musl

[-- Attachment #1: Type: text/plain, Size: 3498 bytes --]

Hi, you can enable cirrus so the CI can be triggered
Also the system emulation didn't support yet:)
Which BIOS would  loongarch64 using? The OpenBIOS?


On Thu, Jun 24, 2021 at 8:18 PM 翟小娟 <zhaixiaojuan@loongson.cn> wrote:
>
> Hi,
> Qemu Loongarch64 related code can be viewed
https://github.com/loongson/qemu/pulls (Add loongarch linux-user emulation
support)
>
>
> -----原始邮件-----
> 发件人:"罗勇刚(Yonggang Luo)" <luoyonggang@gmail.com>
> 发送时间:2021-06-24 19:56:17 (星期四)
> 收件人: Musl <musl@lists.openwall.com>
> 抄送:
> 主题: Re: Re: [musl] Port the new architecture loongarch64 to musl
>
>
>
> On Thu, Jun 24, 2021 at 7:43 PM 翟小娟 <zhaixiaojuan@loongson.cn> wrote:
> &gt;
> &gt; Hi, qemu supports loongarch64 architecture has been completed:
https://github.com/loongson/qemu .
>
> Good to hear that, which qemu branches support for loongarch64?
>
> &gt; For musl loongarch64 source code can also be obtained from
https://github.com/loongson-community/musl. If necessary, we can also
provide a remote testing enviroment.
> &gt; See the attachment for specific modifications.
> &gt;
> &gt; -----原始邮件-----
> &gt; 发件人:"罗勇刚(Yonggang Luo)" <luoyonggang@gmail.com>
> &gt; 发送时间:2021-05-08 00:29:40 (星期六)
> &gt; 收件人: Musl <musl@lists.openwall.com>
> &gt; 抄送: "陈国祺" <chenguoqi@loongson.cn>
> &gt; 主题: Re: [musl] Port the new architecture loongarch64 to musl
> &gt;
> &gt; Same question, does qemu have already support for  loongarch64,
that's means a lot for auto testing
> &gt; As the real hardware will be not broadly  available in the next few
years.
> &gt;
> &gt;
> &gt;
> &gt; On Fri, May 7, 2021 at 5:01 PM 翟小娟 <zhaixiaojuan@loongson.cn> wrote:
> &gt; Hi,
> &gt; I ported a new architecture loongarch64 on the latest branch of musl
master. It has been successfully compiled and run the official test
libraries libc-testsuit and libc-test of musl.
> &gt; The source code of the prot has been published in
https://github.com/loongson-community/musl.  Or check the attachment
0001-port-to-loongarch64.patch, it is the transplanted patch file.
> &gt;
> &gt; Introduction to loongarch architecture:
> &gt; The Loongarch architecture is a simplified instruction computer
style instruction system architecture. The instruction length is fixed and
the encoding format is regular. Most instructions have only two source
operands and one destination operand. The load/store architecture is
adopted, that is, only load/store memory access instructions can access the
memory, and the operation objects of other instructions are all It is the
immediate value in the register or instruction code in the processor core.
> &gt; The Loongson architecture is divided into two versions, 32bit and
64bit, called LA32 and LA64 respectively. LA64 architecture application
level is downward binary compatible with LA32 architecture.
> &gt;
> &gt;
> &gt;
> &gt; --
> &gt; 此致
> &gt; 礼
> &gt; 罗勇刚
> &gt; Yours
> &gt; sincerely,
> &gt; Yonggang Luo
> &gt;
> &gt;
> &gt; </zhaixiaojuan@loongson.cn></chenguoqi@loongson.cn></
musl@lists.openwall.com></luoyonggang@gmail.com>
>
>
>
> --
> 此致
> 礼
> 罗勇刚
> Yours
> sincerely,
> Yonggang Luo
>
>
> </zhaixiaojuan@loongson.cn></musl@lists.openwall.com></
luoyonggang@gmail.com>



--
         此致
礼
罗勇刚
Yours
    sincerely,
Yonggang Luo

[-- Attachment #2: Type: text/html, Size: 5044 bytes --]

^ permalink raw reply	[flat|nested] 14+ messages in thread

end of thread, other threads:[~2021-06-24 12:47 UTC | newest]

Thread overview: 14+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
     [not found] <5f6d09a5.c3a.179460eee20.Coremail.zhaixiaojuan@loongson.cn>
2021-05-07 21:58 ` [musl] Port the new architecture loongarch64 to musl Arnd Bergmann
2021-05-08  5:16   ` 翟小娟
2021-05-09  7:56     ` Arnd Bergmann
     [not found] ` <32e9f7ee-bd3c-762a-a771-2da41a8c1bb0@dereferenced.org>
2021-05-08  5:23   ` 翟小娟
2021-05-08  7:49     ` Ariadne Conill
2021-05-12  9:30       ` 翟小娟
2021-05-12 12:07         ` 罗勇刚(Yonggang Luo)
2021-05-12 19:53         ` Ariadne Conill
2021-05-17 11:19           ` 翟小娟
     [not found] ` <CAE2XoE_9sQrizuiy0afA1dQdPxgOkPda_39oB9DOJN1c2FB0Cw@mail.gmail.com>
2021-05-08  5:18   ` 翟小娟
2021-06-24 11:43   ` 翟小娟
2021-06-24 11:56     ` 罗勇刚(Yonggang Luo)
2021-06-24 12:17       ` 翟小娟
2021-06-24 12:47         ` 罗勇刚(Yonggang Luo)

Code repositories for project(s) associated with this public inbox

	https://git.vuxu.org/mirror/musl/

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).