singrdk/base/Kernel/Native/Buffer.cpp

171 lines
4.5 KiB
C++
Raw Normal View History

2008-03-05 09:52:00 -05:00
////////////////////////////////////////////////////////////////////////////////
//
// Microsoft Research Singularity
//
// Copyright (c) Microsoft Corporation. All rights reserved.
//
// File: Buffer.cpp
//
// Note:
//
#include "hal.h"
void Class_System_Buffer::g_MoveMemory(uint8* dmem, uint8* smem, int size)
{
if (size % 64 == 0 && size >= 64 && (uintptr)dmem % 64 == 0 && (uintptr)smem % 64 == 0) {
g_CopyPages(dmem, smem, size);
return;
}
if (dmem <= smem) {
// make sure the destination is dword aligned
while ((((int)dmem ) & 0x3) != 0 && size >= 3) {
*dmem++ = *smem++;
size -= 1;
}
// copy 16 bytes at a time
if (size >= 16) {
size -= 16;
do {
((int *)dmem)[0] = ((int *)smem)[0];
((int *)dmem)[1] = ((int *)smem)[1];
((int *)dmem)[2] = ((int *)smem)[2];
((int *)dmem)[3] = ((int *)smem)[3];
dmem += 16;
smem += 16;
}
while ((size -= 16) >= 0);
}
// still 8 bytes or more left to copy?
if ((size & 8) != 0) {
((int *)dmem)[0] = ((int *)smem)[0];
((int *)dmem)[1] = ((int *)smem)[1];
dmem += 8;
smem += 8;
}
// still 4 bytes or more left to copy?
if ((size & 4) != 0) {
((int *)dmem)[0] = ((int *)smem)[0];
dmem += 4;
smem += 4;
}
// still 2 bytes or more left to copy?
if ((size & 2) != 0) {
((short *)dmem)[0] = ((short *)smem)[0];
dmem += 2;
smem += 2;
}
// still 1 byte left to copy?
if ((size & 1) != 0) {
dmem[0] = smem[0];
dmem += 1;
smem += 1;
}
} else {
smem += size;
dmem += size;
// make sure the destination is dword aligned
while ((((int)dmem) & 0x3) != 0 && size >= 3) {
*--dmem = *--smem;
size -= 1;
}
// copy 16 bytes at a time
if (size >= 16) {
size -= 16;
do {
dmem -= 16;
smem -= 16;
((int *)dmem)[3] = ((int *)smem)[3];
((int *)dmem)[2] = ((int *)smem)[2];
((int *)dmem)[1] = ((int *)smem)[1];
((int *)dmem)[0] = ((int *)smem)[0];
}
while ((size -= 16) >= 0);
}
// still 8 bytes or more left to copy?
if ((size & 8) != 0) {
dmem -= 8;
smem -= 8;
((int *)dmem)[1] = ((int *)smem)[1];
((int *)dmem)[0] = ((int *)smem)[0];
}
// still 4 bytes or more left to copy?
if ((size & 4) != 0) {
dmem -= 4;
smem -= 4;
((int *)dmem)[0] = ((int *)smem)[0];
}
// still 2 bytes or more left to copy?
if ((size & 2) != 0) {
dmem -= 2;
smem -= 2;
((short *)dmem)[0] = ((short *)smem)[0];
}
// still 1 byte left to copy?
if ((size & 1) != 0) {
dmem -= 1;
smem -= 1;
dmem[0] = smem[0];
}
}
}
void Class_System_Buffer::g_ZeroMemory(uint8* dmem, int size)
{
// Align dmem to 8-bytes for g_ZeroPages
while ((((int)dmem) & 0x7) != 0 && size > 0) {
*dmem++ = 0;
size -= 1;
}
if (size >= 64) {
// g_ZeroPages expects 8-byte alignment and a block size of n*64 bytes.
int toZero = size & ~63;
g_ZeroPages(dmem, toZero);
dmem += toZero;
size -= toZero;
}
if (size >= 16) {
size -= 16;
do {
((int*)dmem)[0] = 0;
((int*)dmem)[1] = 0;
((int*)dmem)[2] = 0;
((int*)dmem)[3] = 0;
dmem += 16;
} while ((size -= 16) >= 0);
}
if ((size & 8) > 0) {
((int*)dmem)[0] = 0;
((int*)dmem)[1] = 0;
dmem += 8;
}
if ((size & 4) > 0) {
((int*)dmem)[0] = 0;
dmem += 4;
}
if ((size & 2) != 0) {
((short*)dmem)[0] = 0;
dmem += 2;
}
if ((size & 1) != 0) {
*dmem++ = 0;
}
}
//
///////////////////////////////////////////////////////////////// End of File.