Hello,
I'm using rsync on RISC-V machines. I notice that the developers of
rsync seem to assume that only x86 CPUs can handle memory misalignments:
```c
/* We know that the x86 can handle misalignment and has the same
* byte order (LSB-first) as the 32-bit numbers we transmit. */
#if defined __i386__ || defined __i486__ || defined __i586__ || defined
__i686__ || __amd64
#define CAREFUL_ALIGNMENT 0
#endif
#ifndef CAREFUL_ALIGNMENT
#define CAREFUL_ALIGNMENT 1
#endif
```
Thus, when copying 4-bit integers (just an example), rsync uses direct
copies on x86:
```c
static inline uint32
IVALu(const uchar *buf, int pos)
{
union {
const uchar *b;
const uint32 *num;
} u;
u.b = buf + pos;
return *u.num;
}
```
On RISC-V (and any other architectures), it copies bytes one by one:
```c
static inline uint32
IVALu(const uchar *buf, int pos)
{
return UVAL(buf, pos)
| UVAL(buf, pos + 1) << 8
| UVAL(buf, pos + 2) << 16
| UVAL(buf, pos + 3) << 24;
}
```
However, it seems that RISC-V supports misaligned memory accesses. I
tested the following code on a RISC-V machine. It worked well.
```c
#include <stdio.h>
int x;
int arr[2], out[2];
int main()
{
arr[0]=0x11223344;
arr[1]=0x55667788;
out[0]=out[1]=0;
x=*(arr);
printf("x=%x\n",x);
x= *(int*)((char *)arr +1);
char *ptr=(char *)out+3;
*(int*)ptr=*(int*)((char *)arr +3);
printf("x2=%x\n",x);
printf("out[0]=%x, out[1]=%x\n",out[0],out[1]);
return 0;
}
```
So, my question is, is CAREFUL_ALIGNMENT=1 necessary for RISC-V?
Although misalignment accesses will suffer from a large time penalty on
RISC-V, I guess it can still run faster than four UVAL calls.
Best regards,
Yuqi Guo
--
Please use reply-all for most replies to avoid omitting the mailing list.
To unsubscribe or change options: https://lists.samba.org/mailman/listinfo/rsync
Before posting, read: http://www.catb.org/~esr/faqs/smart-questions.html