void CPtrList::AddTail(CPtrList* pNewList) { ASSERT_VALID(this); ASSERT_VALID(pNewList); if (pNewList == NULL) { AfxThrowInvalidArgException(); } ASSERT_KINDOF(CPtrList, pNewList); // add a list of same elements POSITION pos = pNewList->GetHeadPosition(); while (pos != NULL) AddTail(pNewList->GetNext(pos)); }
void CPtrList::AddHead(CPtrList* pNewList) { ASSERT_VALID(this); ASSERT_VALID(pNewList); if (pNewList == NULL) { AfxThrowInvalidArgException(); } ASSERT_KINDOF(CPtrList, pNewList); // add a list of same elements to head (maintain order) POSITION pos = pNewList->GetTailPosition(); while (pos != NULL) AddHead(pNewList->GetPrev(pos)); }
void CObList::FreeNode(CObList::CNode* pNode) { if (pNode == NULL) { AfxThrowInvalidArgException(); } pNode->pNext = m_pNodeFree; m_pNodeFree = pNode; m_nCount--; ASSERT(m_nCount >= 0); // make sure we don't underflow // if no more elements, cleanup completely if (m_nCount == 0) RemoveAll(); }
INT_PTR CObArray::Append(const CObArray& src) { ASSERT_VALID(this); ASSERT(this != &src); // cannot append to itself if(this == &src) AfxThrowInvalidArgException(); INT_PTR nOldSize = m_nSize; SetSize(m_nSize + src.m_nSize); Checked::memcpy_s(m_pData + nOldSize, src.m_nSize * sizeof(CObject*), src.m_pData, src.m_nSize * sizeof(CObject*)); return nOldSize; }
void CSharedFile::SetHandle(HGLOBAL hGlobalMemory, BOOL bAllowGrow) { ASSERT(m_hGlobalMemory == NULL); // do once only ASSERT(m_lpBuffer == NULL); // do once only ASSERT(m_nPosition == 0); if (hGlobalMemory == NULL) { AfxThrowInvalidArgException(); } m_hGlobalMemory = hGlobalMemory; m_lpBuffer = (BYTE*)::GlobalLock(m_hGlobalMemory); m_nBufferSize = m_nFileSize = (ULONG)::GlobalSize(m_hGlobalMemory); m_bAllowGrow = bAllowGrow; }
void CStringArray::InsertAt(INT_PTR nStartIndex, const CStringArray* pNewArray) { ASSERT_VALID(this); ASSERT(pNewArray != NULL); ASSERT_KINDOF(CStringArray, pNewArray); ASSERT_VALID(pNewArray); ASSERT(nStartIndex >= 0); if(pNewArray == NULL || nStartIndex < 0) AfxThrowInvalidArgException(); if (pNewArray->GetSize() > 0) { InsertAt(nStartIndex, pNewArray->GetAt(0), pNewArray->GetSize()); for (INT_PTR i = 0; i < pNewArray->GetSize(); i++) SetAt(nStartIndex + i, pNewArray->GetAt(i)); } }
void CStringArray::SetAtGrow(INT_PTR nIndex, const CString& newElement) { ASSERT_VALID(this); ASSERT(nIndex >= 0); if(nIndex < 0) AfxThrowInvalidArgException(); if (nIndex >= m_nSize) { // Make sure newElement is not a reference to an element in the array. // Or else, it will be invalidated by the reallocation. ENSURE( (nIndex < m_nMaxSize) || (&newElement < m_pData) || (&newElement >= (m_pData + m_nMaxSize) ) ); SetSize(nIndex+1); } m_pData[nIndex] = newElement; }
void CStdioFileEx::WriteAnsiString(LPCSTR lpsz) { ASSERT(lpsz != NULL); if (lpsz == NULL) { AfxThrowInvalidArgException(); } if(!m_bIsUnicodeText) { ASSERT(m_pStream != NULL); if (fputs(lpsz, m_pStream) == _TEOF) AfxThrowFileException(CFileException::diskFull, _doserrno, m_strFileName); } else { USES_CONVERSION; WriteWideString(CA2W(lpsz)); } }
void CObArray::RemoveAt(INT_PTR nIndex, INT_PTR nCount) { ASSERT_VALID(this); ASSERT(nIndex >= 0); ASSERT(nCount >= 0); INT_PTR nUpperBound = nIndex + nCount; ASSERT(nUpperBound <= m_nSize && nUpperBound >= nIndex && nUpperBound >= nCount); if(nIndex < 0 || nCount < 0 || (nUpperBound > m_nSize) || (nUpperBound < nIndex) || (nUpperBound < nCount)) AfxThrowInvalidArgException(); // just remove a range INT_PTR nMoveCount = m_nSize - (nUpperBound); if (nMoveCount) { Checked::memmove_s(&m_pData[nIndex], nMoveCount * sizeof(CObject*), &m_pData[nUpperBound], nMoveCount * sizeof(CObject*)); } m_nSize -= nCount; }
void CObArray::InsertAt(INT_PTR nIndex, CObject* newElement, INT_PTR nCount) { ASSERT_VALID(this); ASSERT(nIndex >= 0); // will expand to meet need ASSERT(nCount > 0); // zero or negative size not allowed if(nIndex < 0 || nCount <= 0) AfxThrowInvalidArgException(); if (nIndex >= m_nSize) { // adding after the end of the array SetSize(nIndex + nCount); // grow so nIndex is valid } else { // inserting in the middle of the array INT_PTR nOldSize = m_nSize; SetSize(m_nSize + nCount); // grow it to new size // shift old data up to fill gap Checked::memmove_s(&m_pData[nIndex+nCount], (m_nSize-(nIndex+nCount)) * sizeof(CObject*), &m_pData[nIndex], (nOldSize-nIndex) * sizeof(CObject*)); // re-init slots we copied from memset(&m_pData[nIndex], 0, nCount * sizeof(CObject*)); } // insert new value in the gap ASSERT(nIndex + nCount <= m_nSize); // copy elements into the empty space while (nCount--) m_pData[nIndex++] = newElement; }
void CStringArray::InsertEmpty(INT_PTR nIndex, INT_PTR nCount) { ASSERT_VALID(this); ASSERT(nIndex >= 0); // will expand to meet need ASSERT(nCount > 0); // zero or negative size not allowed if(nIndex < 0 || nCount <= 0) AfxThrowInvalidArgException(); if (nIndex >= m_nSize) { // adding after the end of the array SetSize(nIndex + nCount); // grow so nIndex is valid } else { // inserting in the middle of the array INT_PTR nOldSize = m_nSize; INT_PTR nOverlapSize = min(nCount, nOldSize - nIndex); SetSize(m_nSize + nCount); // grow it to new size // destroy slots we are about to overwrite _DestructElements(&m_pData[m_nSize - nOverlapSize], nOverlapSize); // shift old data up to fill gap Checked::memmove_s(&m_pData[nIndex+nCount], (m_nSize-(nIndex+nCount)) * sizeof(CString), &m_pData[nIndex], (nOldSize-nIndex) * sizeof(CString)); // re-init the now-vacant slots we moved data from _ConstructElements(&m_pData[nIndex], nOverlapSize); } // insert new value in the gap ASSERT(nIndex + nCount <= m_nSize); }
void CStringArray::SetSize(INT_PTR nNewSize, INT_PTR nGrowBy) { ASSERT_VALID(this); ASSERT(nNewSize >= 0); if(nNewSize < 0 ) AfxThrowInvalidArgException(); if (nGrowBy >= 0) m_nGrowBy = nGrowBy; // set new size if (nNewSize == 0) { // shrink to nothing _DestructElements(m_pData, m_nSize); delete[] (BYTE*)m_pData; m_pData = NULL; m_nSize = m_nMaxSize = 0; } else if (m_pData == NULL) { // create one with exact size #ifdef SIZE_T_MAX ASSERT(nNewSize <= SIZE_T_MAX/sizeof(CString)); // no overflow #endif m_pData = (CString*) new BYTE[nNewSize * sizeof(CString)]; _ConstructElements(m_pData, nNewSize); m_nSize = m_nMaxSize = nNewSize; } else if (nNewSize <= m_nMaxSize) { // it fits if (nNewSize > m_nSize) { // initialize the new elements _ConstructElements(&m_pData[m_nSize], nNewSize-m_nSize); } else if (m_nSize > nNewSize) // destroy the old elements _DestructElements(&m_pData[nNewSize], m_nSize-nNewSize); m_nSize = nNewSize; } else { // otherwise, grow array INT_PTR nGrowArrayBy = m_nGrowBy; if (nGrowArrayBy == 0) { // heuristically determine growth when nGrowArrayBy == 0 // (this avoids heap fragmentation in many situations) nGrowArrayBy = min(1024, max(4, m_nSize / 8)); } INT_PTR nNewMax; if (nNewSize < m_nMaxSize + nGrowArrayBy) nNewMax = m_nMaxSize + nGrowArrayBy; // granularity else nNewMax = nNewSize; // no slush ASSERT(nNewMax >= m_nMaxSize); // no wrap around if(nNewMax < m_nMaxSize) AfxThrowInvalidArgException(); #ifdef SIZE_T_MAX ASSERT(nNewMax <= SIZE_T_MAX/sizeof(CString)); // no overflow #endif CString* pNewData = (CString*) new BYTE[(size_t)nNewMax * sizeof(CString)]; // copy new data from old Checked::memcpy_s(pNewData, (size_t)nNewMax * sizeof(CString), m_pData, (size_t)m_nSize * sizeof(CString)); // construct remaining elements ASSERT(nNewSize > m_nSize); _ConstructElements(&pNewData[m_nSize], nNewSize-m_nSize); // get rid of old stuff (note: no destructors called) delete[] (BYTE*)m_pData; m_pData = pNewData; m_nSize = nNewSize; m_nMaxSize = nNewMax; } }