我们在服务器代码上尝试了以下方法,并且吞吐量结果非常糟糕。编码风格和内存分配是否会影响吞吐量性能?我们如何调整它?我需要达到至少55%以上。我使用wireshark测试我的吞吐量,我做了一些设置: 服务器
ethtool -K eth0 tx off
ifdown eth0
ifconfig eth0 mtu 3500
ifup eth0
taskset -c 0 ./server
客户端
ifconfig eth0 mtu 9000
阵 一个。没有填充任何数据。
unsigned long bytetosent = 4080*65536;
char sendBuff[4080 * 65536];
while(x < bytetosent)
{
int bytesWritten = send(connfd, (const char*)sendBuff+x, 6144, 0);
x += 6144;
}
吞吐量:73%
湾填充随机数据
for(int y=0; y<(4080); y++)
{
sendBuff[y] = (rand() %255);
}
while(x < bytetosent)
{
int bytesWritten = send(connfd, (const char*)sendBuff+x, 6144, 0);
x += 6144;
}
吞吐量:53%
MMAP
pImagePool = mmap( (void *)DDR_RAM_PHYS,MAPPED_SIZE_BUFFER, PROT_READ, MAP_SHARED, _fdMem, 0);
while(x < bytetosent)
{
bytesWritten =send(connfd, ((const char*)(pImagePool))+ x, 6144, 0);
x += 6144;
}
吞吐量:20%
的malloc
char *_mBuffer;
_mBuffer = malloc(4080 * 65536);
一个。没有填充任何数据
while(x < bytetosent)
{
bytesWritten =send(connfd, (const char*)_mBuffer+x, 6144, 0);
x += 6144;
}
吞吐量:73%
湾填充随机数据 吞吐量:50%
矢量
vector<char>_pBuffer;
一个。复制
copy((char*)(pImagePool), (((char*)(pImagePool))+1000000), back_inserter(_pBuffer));
bytesWritten = send(connfd, &_pBuffer[bytesSent], bytetosent, MSG_CONFIRM);
bytesSent += bytesWritten;
吞吐量:非常慢
湾的push_back
for(int y=0; y<bytetosent; y++)
{
_pBuffer.push_back(*((char*)pImagePool+y));
}
吞吐量:非常慢
我的服务器连接设置代码:
int listenfd = 0, connfd = 0;
struct sockaddr_in serv_addr;
time_t ticks;
listenfd = socket(AF_INET, SOCK_STREAM, 0);
memset(&serv_addr, '0', sizeof(serv_addr));
serv_addr.sin_family = AF_INET;
serv_addr.sin_addr.s_addr = htonl(INADDR_ANY);
serv_addr.sin_port = htons(8080);
bind(listenfd, (struct sockaddr*)&serv_addr, sizeof(serv_addr));
listen(listenfd, 10);
connfd = accept(listenfd, (struct sockaddr*)NULL, NULL);
我的客户收到代码:
char recvBuff[4080 * 65536];
while ( (n = read(sockfd, recvBuff, sizeof(recvBuff)-1)) > 0)
{
recvBuff[n] = 0;
//printf("\n in while\n");
if(0)//fputs(recvBuff, stdout) == EOF)
{
printf("\n Error : Fputs error\n");
}
}
我尝试使用mmap和memcpy进行时间分析。结果: 它考虑快?
总字节数:40000 * 1088 拍摄时间:0.107197s
代码:
void *pImagePool;
char _cpy[40000 * 1088];
/*Memory Mapping */
const char imagePoolDevice[]="/dev/mem";
int _fdMem;
if( (_fdMem = open( imagePoolDevice, O_RDWR | O_SYNC )) < 0 )
{
printf("Unable to open /dev/mem %d\n", _fdMem);
}
//start
start = chrono::system_clock::now();
pImagePool = mmap(0,MAPPED_SIZE_BUFFER, PROT_READ|PROT_WRITE, MAP_SHARED, _fdMem, DDR_RAM_PHYS);
if( pImagePool == MAP_FAILED ){printf("Mapping Failed\n");}
else{printf("Successful Mapping\n");}
memcpy ( _cpy, &pImagePool, sizeof(_cpy));
//end
end = chrono::system_clock::now();
chrono::duration<double>elapsed_seconds = end - start;
time_t end_time = chrono::system_clock::to_time_t(end);
cout<<"mmap time taken = "<<elapsed_seconds.count()<<endl;
答案 0 :(得分:0)
我终于通过盲测来克服了这个问题,我用以下两种方法进行测试:
我创建一个数组并记忆mmap返回指向数组的指针。它将以太网吞吐量提高了55%。代码如下所示:
char _cpy[40000 * 1088];
pImagePool = mmap(0,MAPPED_SIZE_BUFFER, PROT_READ|PROT_WRITE, MAP_SHARED, _fdMem, DDR_RAM_PHYS);
memcpy ( _cpy, pImagePool, 40000 * 1088);
while(bytesSent != bytetosent)
{
bytesWritten = send(connfd, &_cpy[bytesSent], bytetosent, MSG_CONFIRM);
bytesSent += bytesWritten;
}
复制mmap返回指向vector的指针,但需要先保留矢量大小。很抱歉,我没有在我以前的测试代码中正确执行。以太网吞吐量增加到51%。
vector<char>_pBuffer;
pImagePool = mmap(0,MAPPED_SIZE_BUFFER, PROT_READ|PROT_WRITE, MAP_SHARED, _fdMem, DDR_RAM_PHYS);
_pBuffer.reserve(43520000); //40000 * 1088
copy((char*)pImagePool, (char*)pImagePool + 43520000, back_inserter(_pBuffer));
while(bytesSent != bytetosent)
{
bytesWritten = send(connfd, &_pBuffer[bytesSent], bytetosent, MSG_CONFIRM);
bytesSent += bytesWritten;
}
我不知道这个方法是如何工作的,我只是假设它是复制到内存缓存。