void main(void) { //--- CPU Initialization InitSysCtrl(); // Initialize the CPU DINT; InitPieCtrl(); // Initialize and enable the PIE IER = 0x0000; IFR = 0x0000; InitPieVectTable(); EINT; // Enable Global interrupt INTM ERTM; // Enable Global realtime interrupt DBGM // median() test memcpy_fast(x, y, N<<1); // Start with same data z = 0.0; asm(" NOP"); z = median_SP_RV(x, N); asm(" NOP"); // median_noreorder() test memcpy_fast(x, y, N<<1); // Start with same data z = 0.0; asm(" NOP"); z = median_noreorder_SP_RV(x, N); asm(" NOP"); //--- Main Loop while(1) // Dummy loop. Wait for an interrupt. { asm(" NOP"); } } // end of main()
/* * Swap memory areas */ static void memswap(void *addr1, void *addr2, unsigned long size) { unsigned long off, copy_len; static char buf[1024]; for (off = 0; off < size; off += sizeof(buf)) { copy_len = MIN(size - off, sizeof(buf)); memcpy_fast(buf, (void *) addr2 + off, copy_len); memcpy_fast(addr2 + off, addr1 + off, copy_len); memcpy_fast(addr1 + off, buf, copy_len); } }
BOOL CIndexedHuge::Set(CIndexedDataDescriptor* pcDescriptor) { CIndexedDataDescriptor* pcDescriptorInCache; OIndex oi; oi = pcDescriptor->GetIndex(); pcDescriptorInCache = PrivateGetDescriptor(oi); if (mbDirtyTesting) { if (!pcDescriptorInCache->IsAllocated()) { pcDescriptor->Dirty(TRUE); } else { if (pcDescriptorInCache->IsDirty()) { pcDescriptor->Dirty(TRUE); } else if (!pcDescriptor->IsDirty()) { if (memcmp(pcDescriptor, pcDescriptorInCache, sizeof(CIndexedDataDescriptor)) != 0) { pcDescriptor->Dirty(TRUE); } } } if (pcDescriptor->IsDirty()) { memcpy_fast(pcDescriptorInCache, pcDescriptor, sizeof(CIndexedDataDescriptor)); } } else { memcpy_fast(pcDescriptorInCache, pcDescriptor, sizeof(CIndexedDataDescriptor)); } if (miLastOi < pcDescriptor->GetIndex()) { miLastOi = pcDescriptor->GetIndex(); } return TRUE; }
BOOL CTransientIndexedFile::Add(OIndex oi, void* pvData, unsigned int uiSize) { int iIndex; STransientIndexedPointer* psTransientIndexedPointer; BOOL bExists; void* pvCache; BOOL bResult; bExists = mcPointers.Get(oi, &psTransientIndexedPointer, &iIndex); if (!bExists) { bResult = PrivateAdd(oi, uiSize, &pvCache, iIndex); if (bResult) { memcpy_fast(pvCache, pvData, uiSize); } return bResult; } else { if (psTransientIndexedPointer->IsRemoved()) { return Set(oi, pvData, uiSize); } return FALSE; } }
BOOL CIndexedMemory::Add(OIndex oi, void* pvData, unsigned int uiSize) { int iPos; BOOL bExists; SIndexedMemory* psIndexedMemory; void* pvCache; BOOL bResult; bExists = mcDatas.FindInSorted(&oi, CompareOIndexToTransactionData, &iPos); if (!bExists) { bResult = PrivateAdd(oi, uiSize, &pvCache, iPos); if (bResult) { memcpy_fast(pvCache, pvData, uiSize); } return bResult; } else { psIndexedMemory = (SIndexedMemory*)mcDatas.Get(iPos); if (psIndexedMemory->IsRemoved()) { return Set(oi, pvData, uiSize); } return FALSE; } }
int FifoGet(CMainShare *pMainShare, Fifo *pFifo, unsigned int dest, HANDLE hMutex) { BOOL bGotMutex = FALSE; if(hMutex) { bGotMutex = CriticalRegionEnter(hMutex, 0); } int fifoCount = pFifo->in - pFifo->out; if(fifoCount < 0) { fifoCount += pFifo->FifoSize; } if(fifoCount > 0) { void *src = PosToPtr(pMainShare, pFifo->Pos + pFifo->ulItemSize * pFifo->out); memcpy_fast(dest, src, pFifo->ulItemSize); pFifo->out = (unsigned int)(pFifo->out + 1) % pFifo->FifoSize; } if(bGotMutex) { CriticalRegionLeave(hMutex); } return fifoCount; }
void psxDma3(u32 madr, u32 bcr, u32 chcr) { u32 cdsize; CDVD_LOG("*** DMA 3 *** %lx addr = %lx size = %lx", chcr, madr, bcr); switch (chcr) { case 0x11000000: case 0x11400100: if (cdr.Readed == 0) { CDVD_LOG("*** DMA 3 *** NOT READY"); return; } cdsize = (bcr & 0xffff) * 4; memcpy_fast(iopPhysMem(madr), cdr.pTransfer, cdsize); psxCpu->Clear(madr, cdsize/4); cdr.pTransfer+=cdsize; break; case 0x41000200: //SysPrintf("unhandled cdrom dma3: madr: %x, bcr: %x, chcr %x\n", madr, bcr, chcr); return; default: CDVD_LOG("Unknown cddma %lx", chcr); break; } HW_DMA3_CHCR &= ~0x01000000; psxDmaInterrupt(3); }
void CDependentReadObject::Init(CObjectIdentifier* pcObjectPtr) { CObjectIdentifier* pcThis; pcThis = this; memcpy_fast(pcThis, pcObjectPtr, sizeof(CObjectIdentifier)); miFlags = 0; }
//*************************************************************************** float32 median_noreorder_SP_RV(const float32 *x, Uint16 N) { float32 x_copy[K], y; memcpy_fast(x_copy, x, N<<1); // Copy 2*N 16-bit words on C28x y = median_SP_RV(x_copy, N); // Call median() return(y); } // end of median_noreorder_SP_RV()
/* * Do swap of [crash base - crash base + size] with [0 - crash size] * * We swap all kexec segments except of purgatory. The rest is copied * from [0 - crash size] to [crash base - crash base + size]. * We use [0x2000 - 0x10000] for purgatory. This area is never used * by s390 Linux kernels. * * This functions assumes that the sha256_regions[] is sorted. */ void post_verification_setup_arch(void) { unsigned long start, len, last = crash_base + 0x10000; struct sha256_region *ptr, *end; end = &sha256_regions[sizeof(sha256_regions)/sizeof(sha256_regions[0])]; for (ptr = sha256_regions; ptr < end; ptr++) { if (!ptr->start) continue; start = MAX(ptr->start, crash_base + 0x10000); len = ptr->len - (start - ptr->start); memcpy_fast((void *) last, (void *) last - crash_base, start - last); memswap((void *) start - crash_base, (void *) start, len); last = start + len; } memcpy_fast((void *) last, (void *) last - crash_base, crash_base + crash_size - last); memcpy_fast((void *) crash_base, (void *) 0, 0x2000); }
BOOL CIndexedMemory::Get(OIndex oi, void* pvDest) { BOOL bResult; void* pvData; unsigned int uiSize; bResult = GetDetail(oi, &pvData, &uiSize); if (bResult) { memcpy_fast(pvDest, pvData, uiSize); return TRUE; } return FALSE; }
BOOL CTransientIndexedFile::Get(OIndex oi, void* pvDest) { void* pvData; unsigned int uiSize; BOOL bResult; bResult = GetDetail(oi, &pvData, &uiSize); if (bResult) { memcpy_fast(pvDest, pvData, uiSize); return TRUE; } return FALSE; }
void CGraphicsInstance::Draw(void) { if (!CanDraw()) { return; } //Copy the instances controlling matrix pointers over the objects. This allows object to be drawn at different positions in the safe frame. memcpy_fast(mpcGraphicsObject->GetMatricies()->GetData(), mapMatrices.GetData(), mapMatrices.ByteSize()); //Copy the instances states over the objects. This allows different types of filtering on the same object... is it really necessary? memcpy_fast(mpcGraphicsObject->GetStates()->GetData(), mapStates.GetData(), mapStates.ByteSize()); //Copy the instances materials over the objects. This allows different textures on the same object... memcpy_fast(mpcGraphicsObject->GetMaterials()->GetData(), mapMaterials.GetData(), mapMaterials.ByteSize()); mpcWorld->UseLights(&mapLights); //Draw the updated object. ReverseCullAsNecessary(); mpcGraphicsObject->Draw(); UnreverseCullAsNecessary(); }
int main(){ struct timeval begin,end,result; double time; src = calloc(DATA_SIZE,1); dst = calloc(DATA_SIZE,1); memset(src,0xaa,DATA_SIZE); memset(dst,0xcc,DATA_SIZE); gettimeofday(&begin,NULL); memcpy_fast(dst,src,DATA_SIZE); gettimeofday(&end,NULL); timersub(&end,&begin,&result); printf("Time for copying 1GB data:%d.%03ds\n",result.tv_sec,result.tv_usec/1000); time = result.tv_sec + result.tv_usec * 1e-6; printf("Memcpy bandwidth:%.2fMB/s\n",DATA_SIZE / 1e6 / time); return 0; }
BOOL CIndexedFilesEvictedDescriptorList::GetDescriptor(OIndex oi, CIndexedDataDescriptor* pcDescriptor) { CIndexedDataDescriptor* pcResult; pcResult = mcDescriptors.Get(oi); if (pcResult) { if (pcDescriptor) { memcpy_fast(pcDescriptor, pcResult, sizeof(CIndexedDataDescriptor)); } return TRUE; } else { return FALSE; } }
void CLogFile::CopyWritesToRead(CArrayIntAndPointer* papvOverlapping, filePos iByteSize, void* pvDest) { int i; int iNumWrites; CLogFileCommandWrite* psWrite; int iIndex; void* pvData; filePos iDestOffset; filePos iSourceOffset; void* pvSource; void* pvNewDest; filePos iLength; iNumWrites = papvOverlapping->NumElements(); for (i = 0; i < iNumWrites; i++) { papvOverlapping->Get(i, (void**)&psWrite, &iIndex); pvData = RemapSinglePointer(psWrite, sizeof(CLogFileCommandWrite)); iLength = psWrite->iSize; if ((psWrite->iPosition + psWrite->iSize) > (miPosition + iByteSize)) { iLength -= (psWrite->iPosition + psWrite->iSize) - (miPosition + iByteSize); } iSourceOffset = 0; iDestOffset = psWrite->iPosition - miPosition; if (psWrite->iPosition < miPosition) { iSourceOffset = miPosition - psWrite->iPosition; iDestOffset = 0; } iLength -= iSourceOffset; pvSource = RemapSinglePointer(pvData, (int)iSourceOffset); pvNewDest = RemapSinglePointer(pvDest, (int)iDestOffset); memcpy_fast(pvNewDest, pvSource, (int)iLength); } }
s32 CALLBACK cdvdDmaRead(s32 channel, u32* data, u32 bytesLeft, u32* bytesProcessed) { #ifdef ENABLE_NEW_IOPDMA_CDVD // hacked up from the code above if (cdr.Readed == 0) { //CDVD_LOG("*** DMA 3 *** NOT READY"); wordsProcessed = 0; return 10000; } memcpy_fast(data, cdr.pTransfer, wordsLeft); //psxCpu->Clear(madr, cdsize/4); cdr.pTransfer+=wordsLeft; *wordsProcessed = wordsLeft; Console.WriteLn(Color_Black,"New IOP DMA handled CDVD DMA: channel %d, data %p, remaining %08x, processed %08x.", channel,data,wordsLeft, *wordsProcessed); #endif return 0; }
void xSmartJump::SetTarget() { u8* target = xGetPtr(); if( m_baseptr == NULL ) return; xSetPtr( m_baseptr ); u8* const saveme = m_baseptr + GetMaxInstructionSize(); xJccKnownTarget( m_cc, target, true ); // Copy recompiled data inward if the jump instruction didn't fill the // alloted buffer (means that we optimized things to a j8!) const int spacer = (sptr)saveme - (sptr)xGetPtr(); if( spacer != 0 ) { u8* destpos = xGetPtr(); const int copylen = (sptr)target - (sptr)saveme; memcpy_fast( destpos, saveme, copylen ); xSetPtr( target - spacer ); } }
void CNamedIndexesBlock::Init(int iBlockWidth, void* pvBlocks, filePos iBlockChunkSize, filePos iDataIndex, void* pvCache) { CNamedIndexedBlock* pcBlock; filePos i; miDataIndex = iDataIndex; mpvCachePos = pvCache; miBlockWidth = iBlockWidth; miBlockChunkSize = iBlockChunkSize; mbDirty = FALSE; miUsedBlocks = iBlockChunkSize; memcpy_fast(mpvCachePos, pvBlocks, (size_t)(miUsedBlocks * miBlockWidth)); for (i = 0; i < iBlockChunkSize; i++) { pcBlock = GetUnsafe(i); if (pcBlock->IsEmpty()) { miUsedBlocks = i; break;; } } if (miUsedBlocks == 0) { mszFirst.Init(); mszLast.Init(); } else { pcBlock = GetUnsafe(0); mszFirst.Init(pcBlock->Name()); pcBlock = GetUnsafe(miUsedBlocks - 1); mszLast.Init(pcBlock->Name()); } }
BOOL CIndexedMemory::Set(OIndex oi, void* pvData, unsigned int uiSize) { SIndexedMemory* psIndexedMemory; unsigned int iTotalSize; int iIndex; void* pvCurrent; unsigned int uiCurrentSize; BOOL bExists; if (uiSize > 0) { bExists = PrivateGetDetail(oi, &pvCurrent, &uiCurrentSize, &iIndex); if (!bExists) { return FALSE; } iTotalSize = uiSize + sizeof(SIndexedMemory); if (uiCurrentSize != uiSize) { psIndexedMemory = (SIndexedMemory*)mcDatas.Resize(iIndex, iTotalSize); if (!psIndexedMemory) { return FALSE; } psIndexedMemory->uiSize = uiSize; pvCurrent = RemapSinglePointer(psIndexedMemory, sizeof(SIndexedMemory)); } memcpy_fast(pvCurrent, pvData, uiSize); return TRUE; } else { return FALSE; } }
int FifoAdd(CMainShare *pBase, Fifo *pFifo, void* src, HANDLE hMutex) { if(hMutex) { if(CriticalRegionEnter(hMutex, 0)) { int fifoCount = pFifo->in - pFifo->out; if(fifoCount < 0) { fifoCount += pFifo->FifoSize; } if(fifoCount < pFifo->FifoSize - 1) { void *dest = PosToPtr(pBase, pFifo->Pos + pFifo->ulItemSize * pFifo->in); memcpy_fast(dest, src, pFifo->ulItemSize); pFifo->in = (pFifo->in + 1) % pFifo->FifoSize; return fifoCount + 1; } CriticalRegionLeave(hMutex); } } return -1; }
void SIO_CommandWrite(u8 value,int way) { PAD_LOG("sio write8 %x", value); // PAD COMMANDS switch (sio.padst) { case 1: SIO_INT(); if ((value&0x40) == 0x40) { sio.padst = 2; sio.parp = 1; switch (sio.CtrlReg&0x2002) { case 0x0002: sio.packetsize ++; // Total packet size sent sio.buf[sio.parp] = PADpoll(value); break; case 0x2002: sio.packetsize ++; // Total packet size sent sio.buf[sio.parp] = PADpoll(value); break; } if (!(sio.buf[sio.parp] & 0x0f)) { sio.bufcount = 2 + 32; } else { sio.bufcount = 2 + (sio.buf[sio.parp] & 0x0f) * 2; } } else sio.padst = 0; return; case 2: sio.parp++; switch (sio.CtrlReg&0x2002) { case 0x0002: sio.packetsize ++; sio.buf[sio.parp] = PADpoll(value); break; case 0x2002: sio.packetsize ++; sio.buf[sio.parp] = PADpoll(value); break; } if (sio.parp == sio.bufcount) { sio.padst = 0; return; } SIO_INT(); return; case 3: // No pad connected. sio.parp++; if (sio.parp == sio.bufcount) { sio.padst = 0; return; } SIO_INT(); return; } // MEMORY CARD COMMANDS switch (sio.mcdst) { case 1: { sio.packetsize++; SIO_INT(); if (sio.rdwr) { sio.parp++; return; } sio.parp = 1; const char* log_cmdname = ""; switch (value) { case 0x11: // RESET log_cmdname = "Reset1"; sio.bufcount = 8; memset8<0xff>(sio.buf); sio.buf[3] = sio.terminator; sio.buf[2] = '+'; sio.mcdst = 99; sio2.packet.recvVal3 = 0x8c; break; // FIXME : Why are there two identical cases for resetting the // memorycard(s)? there doesn't appear to be anything dealing with // card slots here. --air case 0x12: // RESET log_cmdname = "Reset2"; sio.bufcount = 8; memset8<0xff>(sio.buf); sio.buf[3] = sio.terminator; sio.buf[2] = '+'; sio.mcdst = 99; sio2.packet.recvVal3 = 0x8c; break; case 0x81: // COMMIT log_cmdname = "Commit"; sio.bufcount = 8; memset8<0xff>(sio.buf); sio.mcdst = 99; sio.buf[3] = sio.terminator; sio.buf[2] = '+'; sio2.packet.recvVal3 = 0x8c; if(value == 0x81) { if(sio.mc_command==0x42) sio2.packet.recvVal1 = 0x1600; // Writing else if(sio.mc_command==0x43) sio2.packet.recvVal1 = 0x1700; // Reading } break; case 0x21: case 0x22: case 0x23: // SECTOR SET log_cmdname = "SetSector"; sio.bufcount = 8; sio.mcdst = 99; sio.sector=0; sio.k=0; memset8<0xff>(sio.buf); sio2.packet.recvVal3 = 0x8c; sio.buf[8]=sio.terminator; sio.buf[7]='+'; break; case 0x24: break; case 0x25: break; case 0x26: { log_cmdname = "GetInfo"; const uint port = sio.GetMemcardIndex(); const uint slot = sio.activeMemcardSlot[port]; mc_command_0x26_tag cmd = mc_sizeinfo_8mb; PS2E_McdSizeInfo info; info.SectorSize = cmd.sectorSize; info.EraseBlockSizeInSectors = cmd.eraseBlocks; info.McdSizeInSectors = cmd.mcdSizeInSectors; SysPlugins.McdGetSizeInfo( port, slot, info ); pxAssumeDev( cmd.mcdSizeInSectors >= mc_sizeinfo_8mb.mcdSizeInSectors, "Mcd plugin returned an invalid memorycard size: Cards smaller than 8MB are not supported." ); cmd.sectorSize = info.SectorSize; cmd.eraseBlocks = info.EraseBlockSizeInSectors; cmd.mcdSizeInSectors = info.McdSizeInSectors; // Recalculate the xor summation // This uses a trick of removing the known xor values for a default 8mb memorycard (for which the XOR // was calculated), and replacing it with our new values. apply_xor( cmd.mc_xor, mc_sizeinfo_8mb.sectorSize ); apply_xor( cmd.mc_xor, mc_sizeinfo_8mb.eraseBlocks ); apply_xor( cmd.mc_xor, mc_sizeinfo_8mb.mcdSizeInSectors ); apply_xor( cmd.mc_xor, cmd.sectorSize ); apply_xor( cmd.mc_xor, cmd.eraseBlocks ); apply_xor( cmd.mc_xor, cmd.mcdSizeInSectors ); sio.bufcount = 12; sio.mcdst = 99; sio2.packet.recvVal3 = 0x83; memset8<0xff>(sio.buf); memcpy_fast(&sio.buf[2], &cmd, sizeof(cmd)); sio.buf[12]=sio.terminator; } break; case 0x27: case 0x28: case 0xBF: log_cmdname = "NotSure"; // FIXME !! sio.bufcount = 4; sio.mcdst = 99; sio2.packet.recvVal3 = 0x8b; memset8<0xff>(sio.buf); sio.buf[4]=sio.terminator; sio.buf[3]='+'; break; // FIXME ? // sio.lastsector and sio.mode are unused. case 0x42: // WRITE log_cmdname = "Write"; //sio.mode = 0; goto __doReadWrite; case 0x43: // READ log_cmdname = "Read"; //sio.lastsector = sio.sector; // Reading goto __doReadWrite; case 0x82: log_cmdname = "Read(?)"; // FIXME !! //if(sio.lastsector==sio.sector) sio.mode = 2; __doReadWrite: sio.bufcount =133; sio.mcdst = 99; memset8<0xff>(sio.buf); sio.buf[133]=sio.terminator; sio.buf[132]='+'; break; case 0xf0: case 0xf1: case 0xf2: log_cmdname = "NoClue"; // FIXME !! sio.mcdst = 99; break; case 0xf3: case 0xf7: log_cmdname = "NoClueHereEither"; // FIXME !! sio.bufcount = 4; sio.mcdst = 99; memset8<0xff>(sio.buf); sio.buf[4]=sio.terminator; sio.buf[3]='+'; break; case 0x52: log_cmdname = "FixMe"; // FIXME !! sio.rdwr = 1; memset8<0xff>(sio.buf); sio.buf[sio.bufcount]=sio.terminator; sio.buf[sio.bufcount-1]='+'; break; case 0x57: log_cmdname = "FixMe"; // FIXME !! sio.rdwr = 2; memset8<0xff>(sio.buf); sio.buf[sio.bufcount]=sio.terminator; sio.buf[sio.bufcount-1]='+'; break; default: log_cmdname = "Unknown"; sio.mcdst = 0; memset8<0xff>(sio.buf); sio.buf[sio.bufcount]=sio.terminator; sio.buf[sio.bufcount-1]='+'; } MEMCARDS_LOG("MC(%d) command 0x%02X [%s]", sio.GetMemcardIndex()+1, value, log_cmdname); sio.mc_command = value; } return; // END CASE 1. // FURTHER PROCESSING OF THE MEMORY CARD COMMANDS case 99: { sio.packetsize++; sio.parp++; switch(sio.mc_command) { // SET_ERASE_PAGE; the next erase commands will *clear* data starting with the page set here case 0x21: // SET_WRITE_PAGE; the next write commands will commit data starting with the page set here case 0x22: // SET_READ_PAGE; the next read commands will return data starting with the page set here case 0x23: if (sio.parp==2)sio.sector|=(value & 0xFF)<< 0; if (sio.parp==3)sio.sector|=(value & 0xFF)<< 8; if (sio.parp==4)sio.sector|=(value & 0xFF)<<16; if (sio.parp==5)sio.sector|=(value & 0xFF)<<24; if (sio.parp==6) { if (sio_xor((u8 *)&sio.sector, 4) == value) MEMCARDS_LOG("MC(%d) SET PAGE sio.sector, sector=0x%04X", sio.GetMemcardIndex()+1, sio.sector); else MEMCARDS_LOG("MC(%d) SET PAGE XOR value ERROR 0x%02X != ^0x%02X", sio.GetMemcardIndex()+1, value, sio_xor((u8 *)&sio.sector, 4)); } break; // SET_TERMINATOR; reads the new terminator code case 0x27: if(sio.parp==2) { sio.terminator = value; sio.buf[4] = value; MEMCARDS_LOG("MC(%d) SET TERMINATOR command, value=0x%02X", sio.GetMemcardIndex()+1, value); } break; // GET_TERMINATOR; puts in position 3 the current terminator code and in 4 the default one // depending on the param case 0x28: if(sio.parp == 2) { sio.buf[2] = '+'; sio.buf[3] = sio.terminator; //if(value == 0) sio.buf[4] = 0xFF; sio.buf[4] = 0x55; MEMCARDS_LOG("MC(%d) GET TERMINATOR command, value=0x%02X", sio.GetMemcardIndex()+1, value); } break; // WRITE DATA case 0x42: if (sio.parp==2) { sio.bufcount=5+value; memset8<0xff>(sio.buf); sio.buf[sio.bufcount-1]='+'; sio.buf[sio.bufcount]=sio.terminator; MEMCARDS_LOG("MC(%d) WRITE command, size=0x%02X", sio.GetMemcardIndex()+1, value); } else if ((sio.parp>2) && (sio.parp<sio.bufcount-2)) { sio.buf[sio.parp]=value; //MEMCARDS_LOG("MC(%d) WRITING 0x%02X", sio.GetMemcardIndex()+1, value); } else if (sio.parp==sio.bufcount-2) { if (sio_xor(&sio.buf[3], sio.bufcount-5)==value) { _SaveMcd(&sio.buf[3], (512+16)*sio.sector+sio.k, sio.bufcount-5); sio.buf[sio.bufcount-1]=value; sio.k+=sio.bufcount-5; } else { MEMCARDS_LOG("MC(%d) write XOR value error 0x%02X != ^0x%02X", sio.GetMemcardIndex()+1, value, sio_xor(&sio.buf[3], sio.bufcount-5)); } } break; // READ DATA case 0x43: if (sio.parp==2) { //int i; sio.bufcount=value+5; sio.buf[3]='+'; MEMCARDS_LOG("MC(%d) READ command, size=0x%02X", sio.GetMemcardIndex()+1, value); _ReadMcd(&sio.buf[4], (512+16)*sio.sector+sio.k, value); /*if(sio.mode==2) { int j; for(j=0; j < value; j++) sio.buf[4+j] = ~sio.buf[4+j]; }*/ sio.k+=value; sio.buf[sio.bufcount-1]=sio_xor(&sio.buf[4], value); sio.buf[sio.bufcount]=sio.terminator; } break; // INTERNAL ERASE case 0x82: if(sio.parp==2) { sio.buf[2]='+'; sio.buf[3]=sio.terminator; //if (sio.k != 0 || (sio.sector & 0xf) != 0) // Console.Warning("saving : odd position for erase."); _EraseMCDBlock((512+16)*(sio.sector&~0xf)); /* memset(sio.buf, -1, 256); _SaveMcd(sio.buf, (512+16)*sio.sector, 256); _SaveMcd(sio.buf, (512+16)*sio.sector+256, 256); _SaveMcd(sio.buf, (512+16)*sio.sector+512, 16); sio.buf[2]='+'; sio.buf[3]=sio.terminator;*/ //sio.buf[sio.bufcount] = sio.terminator; MEMCARDS_LOG("MC(%d) INTERNAL ERASE command 0x%02X", sio.GetMemcardIndex()+1, value); } break; // CARD AUTHENTICATION CHECKS case 0xF0: if (sio.parp==2) { MEMCARDS_LOG("MC(%d) CARD AUTH :0x%02X", sio.GetMemcardIndex()+1, value); switch(value){ case 1: case 2: case 4: case 15: case 17: case 19: sio.bufcount=13; memset8<0xff>(sio.buf); sio.buf[12] = 0; // Xor value of data from index 4 to 11 sio.buf[3]='+'; sio.buf[13] = sio.terminator; break; case 6: case 7: case 11: sio.bufcount=13; memset8<0xff>(sio.buf); sio.buf[12]='+'; sio.buf[13] = sio.terminator; break; default: sio.bufcount=4; memset8<0xff>(sio.buf); sio.buf[3]='+'; sio.buf[4] = sio.terminator; } } break; } if (sio.bufcount<=sio.parp) sio.mcdst = 0; } return; // END CASE 99. } switch (sio.mtapst) { case 0x1: sio.packetsize++; sio.parp = 1; SIO_INT(); switch(value) { case 0x12: // Query number of pads supported. sio.buf[3] = 4; sio.mtapst = 2; sio.bufcount = 5; break; case 0x13: // Query number of memcards supported. sio.buf[3] = 4; sio.mtapst = 2; sio.bufcount = 5; break; case 0x21: // Set pad slot. sio.mtapst = value; sio.bufcount = 6; // No idea why this is 6, saved from old code. break; case 0x22: // Set memcard slot. sio.mtapst = value; sio.bufcount = 6; // No idea why this is 6, saved from old code. break; } // Commented out values are from original code. They break multitap in bios. sio.buf[sio.bufcount-1]=0;//'+'; sio.buf[sio.bufcount]=0;//'Z'; return; case 0x2: sio.packetsize++; sio.parp++; if (sio.bufcount<=sio.parp) sio.mcdst = 0; SIO_INT(); return; case 0x21: // Set pad slot. sio.packetsize++; sio.parp++; sio.mtapst = 2; if (sio.CtrlReg & 2) { int port = sio.GetMultitapPort(); if (IsMtapPresent(port)) sio.activePadSlot[port] = value; } SIO_INT(); return; case 0x22: // Set memcard slot. sio.packetsize++; sio.parp++; sio.mtapst = 2; if (sio.CtrlReg & 2) { int port = sio.GetMultitapPort(); if (IsMtapPresent(port)) sio.activeMemcardSlot[port] = value; } SIO_INT(); return; } if(sio.count == 1 || way == 0) InitializeSIO(value); }
int InputIsoFile::FinishRead3(u8* dst, uint mode) { int _offset, length; int ret = 0; if(m_current_lsn < 0) return -1; if(m_read_inprogress) { ret = m_reader->FinishRead(); m_read_inprogress = false; if(ret < 0) return ret; } switch (mode) { case CDVD_MODE_2352: _offset = 0; length = 2352; break; case CDVD_MODE_2340: _offset = 12; length = 2340; break; case CDVD_MODE_2328: _offset = 24; length = 2328; break; case CDVD_MODE_2048: _offset = 24; length = 2048; break; } int end1 = m_blockofs + m_blocksize; int end2 = _offset + length; int end = std::min(end1, end2); int diff = m_blockofs - _offset; int ndiff = 0; if(diff > 0) { memset(dst, 0, diff); _offset = m_blockofs; } else { ndiff = -diff; diff = 0; } length = end - _offset; uint read_offset = (m_current_lsn - m_read_lsn) * m_blocksize; memcpy_fast(dst + diff, m_readbuffer + ndiff + read_offset, length); if (m_type == ISOTYPE_CD && diff >= 12) { lsn_to_msf(dst + diff - 12, m_current_lsn); dst[diff - 9] = 2; } return 0; }
// FIXME: why is this not in soft filter management? bool copy_packet_to_user(struct buffer_descriptor *buffer, void *data, uint64_t len, uint64_t flags) { // Must only be called if we use software filtering assert(use_sf); assert(len > 0); assert(data != NULL); assert(buffer != NULL); struct net_queue_manager_binding *b = buffer->con; assert(b != NULL); struct client_closure *cl = (struct client_closure *) b->st; assert(cl != NULL); // check if there are slots which can be used in app (!isempty) if(buffer->rxq.buffer_state_used == 0) { printf("[%s] Dropping packet as no space in userspace " "2cp pkt buf [%" PRIu64 "]: " "size[%zu] used[%zu], after [%"PRIu64"] sent" " added [%"PRIu64"] \n", disp_name(), buffer->buffer_id, buffer->rxq.buffer_state_size, buffer->rxq.buffer_state_used, sent_packets, rx_added); if (cl->debug_state == 4) { ++cl->in_dropped_app_buf_full; } //abort(); // optional, should be removed return false; } if (!is_enough_space_in_queue(cl->q)) { printf("[%s] Dropping packet as app [%d] is not processing packets" "fast enough. Cont queue is almost full [%d], pkt count [%"PRIu64"]\n", disp_name(), cl->cl_no, queue_free_slots(cl->q), sent_packets); if (cl->debug_state == 4) { ++cl->in_dropped_app_buf_full; } // abort(); // FIXME: temparary halt to simplify debugging return false; } // pop the latest buffer from head of queue (this is stack) --buffer->rxq.buffer_state_head; struct buffer_state_metadata *bsm = buffer->rxq.buffer_state + buffer->rxq.buffer_state_head; assert(bsm != NULL); uint64_t offset = bsm->offset; --buffer->rxq.buffer_state_used; assert(offset < buffer->bytes); void *dst = (void *) (uintptr_t) buffer->va + offset; ETHERSRV_DEBUG("Copy packet pos %p %p %p\n", buffer->va, dst, (buffer->va + buffer->bytes)); uint64_t ts = rdtsc(); memcpy_fast((void *) (uintptr_t)dst, data, len); if (cl->debug_state == 4) { netbench_record_event_simple(bm, RE_COPY, ts); } ++sent_packets; // FIXME: remove this! // add trace pkt cpy #if TRACE_ETHERSRV_MODE uint32_t pkt_location = (uint32_t) ((uintptr_t) data); trace_event(TRACE_SUBSYS_NNET, TRACE_EVENT_NNET_NI_PKT_CPY, pkt_location); #endif // TRACE_ETHERSRV_MODE // Handle raw interface errval_t err = send_raw_xmit_done(b, offset, len, 0, flags); if (err_is_ok(err)) { return true; } else { // As application is not able to process the packet // we will drop this one USER_PANIC("send_raw_xmit_done failed as queue full, can't go further: 2\n"); // FIXME: Don't crash. ignore the packet, undo any changes done by it // and continue. Ideally this shouldn't happen as we are checking for // free space before actually sending the packt. return false; } return true; } // end function: copy_packet_to_user
int __cdecl IniLoadFile(int *ModelTable, int *pulModelTableCount, void **a3, int a4, LPCSTR lpFileName, __int16 a6, int a7) { char v7; // ST1C_1@9 char v9; // ST1C_1@13 DWORD v10; // eax@17 DWORD v11; // eax@41 signed int v12; // eax@44 int v13; // eax@44 BlowfishBlock *v14; // eax@50 int v15; // edx@50 BlowfishBlock *v16; // eax@59 int v17; // edx@59 char v18; // [sp+20h] [bp-31C8h]@59 int ctx; // [sp+28h] [bp-31C0h]@50 char v20; // [sp+30h] [bp-31B8h]@44 BlowfishPad v21; // [sp+1078h] [bp-2170h]@44 SIZE_T nNumberOfBytesToWrite; // [sp+20C0h] [bp-1128h]@57 DWORD NumberOfBytesWritten; // [sp+20C4h] [bp-1124h]@57 HANDLE hFile; // [sp+20C8h] [bp-1120h]@56 LPCVOID lpBuffer; // [sp+20CCh] [bp-111Ch]@56 int L; // [sp+20D0h] [bp-1118h]@50 int R; // [sp+20D4h] [bp-1114h]@50 void *v28; // [sp+20D8h] [bp-1110h]@54 unsigned int byteSize; // [sp+20DCh] [bp-110Ch]@45 int dest; // [sp+20E0h] [bp-1108h]@45 unsigned int v31; // [sp+20E4h] [bp-1104h]@45 BlowfishBlock chain; // [sp+20E8h] [bp-1100h]@44 BlowfishPad pad; // [sp+20F0h] [bp-10F8h]@44 int cnt; // [sp+3138h] [bp-B0h]@60 int i; // [sp+313Ch] [bp-ACh]@60 char key; // [sp+3140h] [bp-A8h]@44 __int16 v37; // [sp+316Ch] [bp-7Ch]@44 unsigned int v38; // [sp+3170h] [bp-78h]@1 unsigned int j; // [sp+3174h] [bp-74h]@85 DWORD Buffer; // [sp+3178h] [bp-70h]@34 _BYTE *lpMem; // [sp+317Ch] [bp-6Ch]@1 ModelTable *v42; // [sp+3180h] [bp-68h]@1 SIZE_T nNumberOfBytesToRead; // [sp+3184h] [bp-64h]@31 int ulCount; // [sp+3188h] [bp-60h]@1 HANDLE hObject; // [sp+318Ch] [bp-5Ch]@30 ModelTable v46; // [sp+3190h] [bp-58h]@82 int v47; // [sp+31DCh] [bp-Ch]@85 char v48[4]; // [sp+31E0h] [bp-8h]@1 int v49; // [sp+31E4h] [bp-4h]@1 int v50; // [sp+31E8h] [bp+0h]@1 v38 = (unsigned int)&v50 ^ dword_10072570; lpMem = 0; v49 = 0; v42 = 0; ulCount = 0; *(_DWORD *)v48 = 0; if ( g_LogEvents ) { if ( DebugMsg1("IniLoadFile") ) DebugMsg3("Entry - '%s'.", (char)lpFileName); } if ( !lpFileName || !ModelTable || !pulModelTableCount ) { if ( DebugMsg1("IniLoadFile") ) CheckAssert("NULL Pointer.", v7); return 0; } if ( !*lpFileName ) { if ( DebugMsg1("IniLoadFile") ) CheckAssert("EMPTY String.", v9); return 0; } v42 = (ModelTable *)HeapAlloc(g_hHeap, 8u, 0x11000u); if ( !v42 ) { if ( DebugMsg1("IniLoadFile") ) { v10 = GetLastError(); CheckAssert("Failed to allocated %d bytes. Reason:%d.", 0, v10); } return 0; } if ( *ModelTable && (unsigned int)*pulModelTableCount < 0x400 ) { ulCount = *pulModelTableCount; memcpy_fast((unsigned int)v42, *ModelTable, 0x44 * ulCount); HeapFree(g_hHeap, 0, (LPVOID)*ModelTable); if ( !ulCount ) { if ( DebugMsg1("IniLoadFile") ) CheckAssert("%s - %s line %d: assert %s\n", (unsigned int)"IniLoadFile", ".\\IniMgr.cpp", 1598, "ulCount > 0"); } if ( DebugMsg1("IniLoadFile") ) DebugMsg2(131072, "IniLoadFilesFromPath - Found %d device from previous file(s).\n", ulCount); } else { ulCount = 0; if ( *pulModelTableCount ) { if ( DebugMsg1("IniLoadFile") ) CheckAssert( "%s - %s line %d: assert %s\n", (unsigned int)"IniLoadFile", ".\\IniMgr.cpp", 1604, "*pulModelTableCount == 0"); } } hObject = CreateFileA(lpFileName, 0x80000000u, 0, 0, 3u, 0x80u, 0); if ( hObject != (HANDLE)-1 ) { nNumberOfBytesToRead = GetFileSize(hObject, 0); if ( nNumberOfBytesToRead != -1 ) lpMem = HeapAlloc(g_hHeap, 8u, nNumberOfBytesToRead); if ( lpMem ) { if ( ReadFile(hObject, lpMem, nNumberOfBytesToRead, &Buffer, 0) == 1 ) { if ( DebugMsg1("IniLoadFile") ) DebugMsg2(131072, "IniLoadFilesFromPath - Read %d bytes from file.\n", Buffer); } else { if ( DebugMsg1("IniLoadFile") ) CheckAssert("%s - %s line %d: assert %s\n", (unsigned int)"IniLoadFile", ".\\IniMgr.cpp", 1632, "FALSE"); if ( DebugMsg1("IniLoadFile") ) { v11 = GetLastError(); DebugMsg2(131072, "IniLoadFilesFromPath - ReadFile Failed %d.\n", v11); } HeapFree(g_hHeap, 0, lpMem); lpMem = 0; } } CloseHandle(hObject); if ( lpMem ) { memcpy(&key, "SetPoint-83918EEE-DB31-4df1-B11D-F93932DBC1B8", 44u); v37 = *(_WORD *)&aSetpoint83918e[44]; v12 = strlen(&key); v13 = BlowfishGeneratePad((int)&v20, (int)&key, v12); memcpy_fast((unsigned int)&v21, v13, 0x1048u); memcpy_fast((unsigned int)&pad, (int)&v21, 0x1048u); BlowfishBlock__ctor(&chain, 0xC009F158u, 0x17EC17ECu); if ( strncmp(lpMem, ";KHAL", 5u) ) { dest = 0; v31 = *(_DWORD *)lpMem; byteSize = GetBlockSizeOfBuffer(v31, 8u); if ( Buffer != byteSize + 12 || v31 > byteSize ) { HeapFree(g_hHeap, 0, lpMem); goto LABEL_101; } dest = (int)HeapAlloc(g_hHeap, 8u, byteSize + 1); if ( !dest ) { HeapFree(g_hHeap, 0, lpMem); goto LABEL_101; } BlowfishDecryptCBC(&pad, (int)(lpMem + 4), dest, byteSize, &chain); v14 = BlowfishEncipherBlock((int)&ctx, &pad, &chain); v15 = v14->R; chain.L = v14->L; chain.R = v15; L = *(_DWORD *)&lpMem[byteSize + 4]; R = *(_DWORD *)&lpMem[byteSize + 8]; if ( chain.L != L || chain.R != R ) { if ( DebugMsg1("IniLoadFile") ) CheckAssert( "%s - %s line %d: assert %s\n", (unsigned int)"IniLoadFile", ".\\IniMgr.cpp", 1681, "chain.L == L && chain.R == R"); } v28 = lpMem; lpMem = (_BYTE *)dest; HeapFree(g_hHeap, 0, v28); Buffer = v31; } else { if ( a6 & 0x400 ) { lpBuffer = 0; hFile = CreateFileA(lpFileName, 0x40000000u, 0, 0, 2u, 0x80u, 0); if ( hFile != (HANDLE)-1 ) { nNumberOfBytesToWrite = GetBlockSizeOfBuffer(Buffer, 8u); lpBuffer = HeapAlloc(g_hHeap, 8u, nNumberOfBytesToWrite); WriteFile(hFile, &Buffer, 4u, &NumberOfBytesWritten, 0); if ( lpBuffer ) { BlowfishDecryptCFB(&pad, (int)lpMem, (int)lpBuffer, nNumberOfBytesToWrite, &chain); WriteFile(hFile, lpBuffer, nNumberOfBytesToWrite, &NumberOfBytesWritten, 0); HeapFree(g_hHeap, 0, (LPVOID)lpBuffer); } v16 = BlowfishEncipherBlock((int)&v18, &pad, &chain); v17 = v16->R; chain.L = v16->L; chain.R = v17; WriteFile(hFile, &chain, 4u, &NumberOfBytesWritten, 0); WriteFile(hFile, &chain.R, 4u, &NumberOfBytesWritten, 0); CloseHandle(hFile); } } } cnt = 0; i = -1; while ( cnt < (signed int)Buffer ) { if ( lpMem[cnt] == ';' ) { for ( i = cnt + 1; i < (signed int)Buffer && lpMem[i] != '\r' && lpMem[i] != '\n'; ++i ) ; while ( i < (signed int)Buffer && (lpMem[i] == '\r' || lpMem[i] == '\n') ) ++i; if ( i < (signed int)Buffer ) memcpy_fast((unsigned int)&lpMem[cnt], (int)&lpMem[i], Buffer - i); Buffer -= i - cnt; } else { ++cnt; } } cnt = -1; for ( i = 0; i < (signed int)Buffer; ++i ) { if ( lpMem[i] == '[' || i == Buffer - 1 ) { if ( cnt >= 0 ) { lpMem[i - 1] = 0; memset(&v46, 0, 0x44u); if ( IniLoadUnsupportedSection(a3, (_DWORD *)a4, &lpMem[cnt]) != 1 ) { if ( IniLoadSection(&v46, (int)&lpMem[cnt]) == 1 ) { v47 = 1; for ( j = 0; j < ulCount; ++j ) { if ( v46.field_0 == v42[j].field_0 && v46.field_4 == v42[j].field_4 ) { IniFreeModelInfo((unsigned int)&v46, (int)v42, &v46); if ( a7 ) { if ( dword_10072548 ) { if ( DebugMsg1("IniLoadFile") ) sub_1003DBE0("Model Overwrite (%08X-%X).\n", *(_QWORD *)&v46); } } v47 = 0; break; } } if ( v47 ) { memcpy(&v42[ulCount++], &v46, sizeof(v42[ulCount++])); ++*(_DWORD *)v48; } } } } cnt = i; } } HeapFree(g_hHeap, 0, lpMem); lpMem = 0; goto LABEL_101; } } LABEL_101: if ( ulCount ) { *ModelTable = (int)HeapAlloc(g_hHeap, 8u, 68 * ulCount); if ( *ModelTable ) { memcpy_fast(*ModelTable, (int)v42, 68 * ulCount); *pulModelTableCount = ulCount; } else { if ( DebugMsg1("IniLoadFile") ) CheckAssert("%s - %s line %d: assert %s\n", (unsigned int)"IniLoadFile", ".\\IniMgr.cpp", 1840, "FALSE"); *pulModelTableCount = 0; } } else { *pulModelTableCount = 0; *ModelTable = 0; } HeapFree(g_hHeap, 0, v42); v42 = 0; if ( g_LogEvents ) { if ( DebugMsg1("IniLoadFile") ) DebugMsg3("Exit %d.", v48[0]); } return *(_DWORD *)v48; }
BOOL CTransientIndexedFile::Set(OIndex oi, void* pvData, unsigned int uiSize) { STransientIndexedPointer* psPointer; SOIndexIndexCacheDescriptor* psCacheDesc; void* pvCache; int iPointerIndex; BOOL bExists; int iIndex; BOOL bResult; bExists = mcPointers.Get(oi, &psPointer, &iIndex); if (!bExists) { return FALSE; } if (uiSize > 0) { if (uiSize != psPointer->sIndexedMemory.uiSize) { if (psPointer->pvCache) { psCacheDesc = (SOIndexIndexCacheDescriptor*)RemapSinglePointer(psPointer->pvCache, -(int)sizeof(SOIndexIndexCacheDescriptor)); mcCache.Invalidate(psCacheDesc); } psPointer->sIndexedMemory.uiSize = uiSize; bResult = Allocate(psPointer, iIndex); if (bResult) { pvCache = psPointer->pvCache; memcpy_fast(pvCache, pvData, uiSize); return TRUE; } return FALSE; } else { if (psPointer->pvCache) { pvCache = psPointer->pvCache; } else { bResult = Allocate(psPointer, iIndex); if (!bResult) { return FALSE; } pvCache = psPointer->pvCache; } } iPointerIndex = mcPointers.GetIndex(psPointer); if (pvCache) { psCacheDesc = (SOIndexIndexCacheDescriptor*)RemapSinglePointer(pvCache, -(int)(sizeof(SOIndexIndexCacheDescriptor))); psCacheDesc->sIndex.iIndex = iPointerIndex; psCacheDesc->sIndex.oi = psPointer->sIndexedMemory.oi; memcpy_fast(pvCache, pvData, uiSize); psPointer->Init(oi, uiSize); psPointer->pvCache = pvCache; return TRUE; } return FALSE; } else { return FALSE; } }
void I_FinishUpdate (void) { //e6y: new mouse code UpdateGrab(); // The screen wipe following pressing the exit switch on a level // is noticably jerkier with I_SkipFrame // if (I_SkipFrame())return; #ifdef MONITOR_VISIBILITY if (!(SDL_GetAppState()&SDL_APPACTIVE)) { return; } #endif #ifdef GL_DOOM if (V_GetMode() == VID_MODEGL) { // proff 04/05/2000: swap OpenGL buffers gld_Finish(); return; } #endif if ((screen_multiply > 1) || SDL_MUSTLOCK(screen)) { int h; byte *src; byte *dest; if (SDL_LockSurface(screen) < 0) { lprintf(LO_INFO,"I_FinishUpdate: %s\n", SDL_GetError()); return; } // e6y: processing of screen_multiply if (screen_multiply > 1) { R_ProcessScreenMultiply(screens[0].data, screen->pixels, V_GetPixelDepth(), screens[0].byte_pitch, screen->pitch); } else { dest=screen->pixels; src=screens[0].data; h=screen->h; for (; h>0; h--) { memcpy_fast(dest,src,SCREENWIDTH*V_GetPixelDepth()); //e6y dest+=screen->pitch; src+=screens[0].byte_pitch; } } SDL_UnlockSurface(screen); } /* Update the display buffer (flipping video pages if supported) * If we need to change palette, that implicitely does a flip */ if (newpal != NO_PALETTE_CHANGE) { I_UploadNewPalette(newpal, false); newpal = NO_PALETTE_CHANGE; } #ifdef GL_DOOM if (vid_8ingl.enabled) { gld_Draw8InGL(); } else #endif { SDL_Flip(screen); } }
void CImageAccessor::Get(int x, int y, void* pvDest) { void* pvData; pvData = Get(x, y); memcpy_fast(pvDest, pvData, mpcAccessor->GetBufferSize()); }
void cdrReadInterrupt() { u8 *buf; if (!cdr.Reading) return; if (cdr.Stat) { CDREAD_INT(0x800); return; } CDR_LOG("KEY END"); cdr.OCUP = 1; SetResultSize(1); cdr.StatP|= 0x22; cdr.Result[0] = cdr.StatP; SysPrintf("Reading From CDR"); buf = CDVDgetBuffer(); if (buf == NULL) cdr.RErr = -1; if (cdr.RErr == -1) { CDR_LOG(" err\n"); memzero_ptr<2340>(cdr.Transfer); cdr.Stat = DiskError; cdr.Result[0]|= 0x01; ReadTrack(); CDREAD_INT((cdr.Mode & 0x80) ? (cdReadTime / 2) : cdReadTime); return; } memcpy_fast(cdr.Transfer, buf+12, 2340); cdr.Stat = DataReady; CDR_LOG(" %x:%x:%x\n", cdr.Transfer[0], cdr.Transfer[1], cdr.Transfer[2]); cdr.SetSector[2]++; if (cdr.SetSector[2] == 75) { cdr.SetSector[2] = 0; cdr.SetSector[1]++; if (cdr.SetSector[1] == 60) { cdr.SetSector[1] = 0; cdr.SetSector[0]++; } } cdr.Readed = 0; if ((cdr.Transfer[4+2] & 0x80) && (cdr.Mode & 0x2)) { // EOF CDR_LOG("AutoPausing Read\n"); AddIrqQueue(CdlPause, 0x800); } else { ReadTrack(); CDREAD_INT((cdr.Mode & 0x80) ? (cdReadTime / 2) : cdReadTime); } psxHu32(0x1070)|= 0x4; return; }
BOOL CLogFile::AmalgamateOverlappingWrites(CArrayIntAndPointer* papvOverlapping, const void* pvSource, filePos iPosition, filePos iLength) { filePos iStart; filePos iEnd; //Inclusive; int i; CLogFileCommandWrite* psWrite; int iIndex; filePos iIndeedSize; CLogFileCommandWrite* psCommand; void* pvData; void* pvDest; void* pvNewSource; //Find the total size of the write chunk. iStart = iPosition; iEnd = iPosition + iLength - 1; for (i = 0; i < papvOverlapping->NumElements(); i++) { papvOverlapping->Get(i, (void**)&psWrite, &iIndex); if (psWrite->iPosition < iStart) { iStart = psWrite->iPosition; } if ((psWrite->iPosition + psWrite->iSize - 1) > iEnd) { iEnd = psWrite->iPosition + psWrite->iSize - 1; } } iIndeedSize = iEnd - iStart + 1; //Allocate enough memory for the new chunk. psCommand = AddWriteCommand(iStart, iIndeedSize); if (!psCommand) { return FALSE; } pvData = RemapSinglePointer(psCommand, sizeof(CLogFileCommandWrite)); //Copy all the overlapping chunks into the new one. for (i = 0; i < papvOverlapping->NumElements(); i++) { iIndex = papvOverlapping->GetType(i); psWrite = (CLogFileCommandWrite*)macCommands.Get(iIndex); pvDest = RemapSinglePointer(pvData, (int)(psWrite->iPosition - iStart)); pvNewSource = RemapSinglePointer(psWrite, sizeof(CLogFileCommandWrite)); memcpy_fast(pvDest, pvNewSource, (int)psWrite->iSize); } pvDest = RemapSinglePointer(pvData, (int)(iPosition - iStart)); memcpy_fast(pvDest, (void*)pvSource, (size_t)iLength); //Remove all the old overlapping chunks. for (i = papvOverlapping->NumElements()-1; i >= 0; i--) { iIndex = papvOverlapping->GetType(i); macCommands.RemoveAt(iIndex, TRUE); } return TRUE; }