相关疑难解决方法(0)

清除一个小整数数组:memset与for循环

有两种方法可以将整数/浮点数组清零:

memset(array, 0, sizeof(int)*arraysize);
Run Code Online (Sandbox Code Playgroud)

要么:

for (int i=0; i <arraysize; ++i)
    array[i]=0;
Run Code Online (Sandbox Code Playgroud)

显然,memset对于大型更快arraysize.但是,在什么时候memset的开销实际上大于for循环的开销?例如,对于大小为5的数组 - 哪个最好?第一个,第二个,甚至可能是未滚动的版本:

array[0] = 0;
array[1] = 0;
array[2] = 0;
array[3] = 0;
array[4] = 0;
Run Code Online (Sandbox Code Playgroud)

c performance benchmarking

56
推荐指数
3
解决办法
6万
查看次数

为memcpy增强了REP MOVSB

我想使用增强的REP MOVSB(ERMSB)为自定义获得高带宽memcpy.

ERMSB引入了Ivy Bridge微体系结构.如果您不知道ERMSB是什么,请参阅英特尔优化手册中的"增强型REP MOVSB和STOSB操作(ERMSB)" 部分.

我知道直接执行此操作的唯一方法是使用内联汇编.我从https://groups.google.com/forum/#!topic/gnu.gcc.help/-Bmlm_EG_fE获得了以下功能

static inline void *__movsb(void *d, const void *s, size_t n) {
  asm volatile ("rep movsb"
                : "=D" (d),
                  "=S" (s),
                  "=c" (n)
                : "0" (d),
                  "1" (s),
                  "2" (n)
                : "memory");
  return d;
}
Run Code Online (Sandbox Code Playgroud)

然而,当我使用它时,带宽远小于memcpy. 使用我的i7-6700HQ(Skylake)系统,Ubuntu 16.10,DDR4 @ 2400 MHz双通道32 GB,GCC 6.2,__movsb获得15 GB/s并memcpy获得26 GB/s.

为什么带宽如此低REP MOVSB?我该怎么做才能改善它?

这是我用来测试它的代码.

//gcc -O3 -march=native -fopenmp foo.c
#include <stdlib.h>
#include <string.h>
#include <stdio.h>
#include …
Run Code Online (Sandbox Code Playgroud)

c x86 assembly gcc memcpy

56
推荐指数
4
解决办法
1万
查看次数

将struct转换为byte并返回struct

我目前正在使用Arduino Uno,9DOF和XBee,我正在尝试创建一个结构,可以通过串行,逐字节发送,然后重新构造成结构.

到目前为止,我有以下代码:

struct AMG_ANGLES {
    float yaw;
    float pitch;
    float roll;
};

int main() {
    AMG_ANGLES struct_data;

    struct_data.yaw = 87.96;
    struct_data.pitch = -114.58;
    struct_data.roll = 100.50;

    char* data = new char[sizeof(struct_data)];

    for(unsigned int i = 0; i<sizeof(struct_data); i++){
        // cout << (char*)(&struct_data+i) << endl;
        data[i] = (char*)(&struct_data+i); //Store the bytes of the struct to an array.
    }

    AMG_ANGLES* tmp = (AMG_ANGLES*)data; //Re-make the struct
    cout << tmp.yaw; //Display the yaw to see if it's correct. …
Run Code Online (Sandbox Code Playgroud)

c++ byte struct arduino xbee

21
推荐指数
3
解决办法
5万
查看次数

组装:REP MOV机制

查看以下汇编代码:

MOV ESI, DWORD PTR [EBP + C]
MOV ECX, EDI
MOV EAX, EAX
SHR ECX, 2
LEA EDI, DWORD PTR[EBX + 18]
REP MOVS DWORD PTR ES:[EDI], DWORD PTR [ESI]
MOV ECX, EAX
AND ECX, 3
REP MOVS BYTE PTR ES:[EDI], BYTE PTR[ESI]
Run Code Online (Sandbox Code Playgroud)

我得到代码摘录的书解释了第一个REP MOVS复制4字节块,第二个REP MOVS复制剩余的2字节块(如果存在).

REP MOVS说明书如何运作?根据MSDN,"该指令可以用REP作为前缀,重复操作ecx寄存器指定的次数." 难道不会一遍又一遍地重复同样的操作吗?

x86 assembly

8
推荐指数
2
解决办法
2万
查看次数

在 x86 和 ARM 中移动内存的最佳方式?

我很想知道在 x86 架构上进行大容量内存复制的最佳方法。我意识到这取决于机器特定的特性。主要目标是过去 4-5 年制造的典型台式机。

我知道在过去,带有 REPE 的 MOVSD 名义上是最快的方法,因为您一次可以移动 4 个字节,但我已经读到,现在 MOVSB 一样快并且编写起来更简单,所以您也可以做一个字节移动并忘记 4 字节移动的复杂性。

一个周围的问题是 MOVxx 指令是否值得。如果 CPU 的运行速度比内存总线快得多,那么使用 CISC 移动可能毫无意义,您也可以使用普通的 MOV。这将是最有吸引力的,因为这样我就可以在其他处理器架构(如 ARM)上使用相同的算法。这带来了一个类似的问题,即 ARM 用于大容量内存移动的专用指令(与 Intel 完全不同)是否值得。


注意:我已阅读英特尔优化参考手册中的 3.7.6 节,因此我熟悉基础知识。我希望有人能将本手册内容以外的领域的实践经验联系起来。

optimization x86 assembly arm

0
推荐指数
1
解决办法
2425
查看次数

gcc高效字节复制ARM Cortex M4

是否有内置的gccmemcopy功能,专门针对ARM Cortex M4的架构进行了优化?

assembly arm cortex-m

0
推荐指数
1
解决办法
210
查看次数

标签 统计

assembly ×4

x86 ×3

arm ×2

c ×2

arduino ×1

benchmarking ×1

byte ×1

c++ ×1

cortex-m ×1

gcc ×1

memcpy ×1

optimization ×1

performance ×1

struct ×1

xbee ×1