String ReadLine(FILE *infile) { String line, nline; int n, ch, size; n = 0; size = InitialBufferSize; line = GetBlock(size + 1); while ((ch = getc(infile)) != '\n' && ch != EOF) { if (n == size) { size *= 2; nline = (String) GetBlock(size + 1); strncpy(nline, line, n); FreeBlock(line); line = nline; } line[n++] = ch; } if (n == 0 && ch == EOF) { FreeBlock(line); return (NULL); } line[n] = '\0'; nline = (String) GetBlock(n + 1); strcpy(nline, line); FreeBlock(line); return (nline); }
void BlockCacheConcurrencyTest::TestBlockCache(BBlockCache *theCache, bool isMallocTest) { BList cacheList; BList nonCacheList; thread_id theThread = find_thread(NULL); // Do everything eight times to ensure the test runs long // enough to check for concurrency problems. for (int j = 0; j < 8; j++) { // Perform a series of gets, saves and frees for (int i = 0; i < numBlocksInCache / 2; i++) { GetBlock(theCache, sizeOfBlocksInCache, theThread, &cacheList, &nonCacheList); GetBlock(theCache, sizeOfBlocksInCache, theThread, &cacheList, &nonCacheList); GetBlock(theCache, sizeOfNonCacheBlocks, theThread, &cacheList, &nonCacheList); GetBlock(theCache, sizeOfNonCacheBlocks, theThread, &cacheList, &nonCacheList); SaveBlock(theCache, cacheList.ItemAt(cacheList.CountItems() / 2), sizeOfBlocksInCache, theThread, &cacheList, &nonCacheList); SaveBlock(theCache, nonCacheList.ItemAt(nonCacheList.CountItems() / 2), sizeOfNonCacheBlocks, theThread, &cacheList, &nonCacheList); GetBlock(theCache, sizeOfBlocksInCache, theThread, &cacheList, &nonCacheList); GetBlock(theCache, sizeOfBlocksInCache, theThread, &cacheList, &nonCacheList); GetBlock(theCache, sizeOfNonCacheBlocks, theThread, &cacheList, &nonCacheList); GetBlock(theCache, sizeOfNonCacheBlocks, theThread, &cacheList, &nonCacheList); FreeBlock(cacheList.ItemAt(cacheList.CountItems() / 2), sizeOfBlocksInCache, isMallocTest, theThread, &cacheList, &nonCacheList); FreeBlock(nonCacheList.ItemAt(nonCacheList.CountItems() / 2), sizeOfNonCacheBlocks, isMallocTest, theThread, &cacheList, &nonCacheList); } bool performFree = false; // Free or save (every other block) for all "cache sized" blocks. while (!cacheList.IsEmpty()) { if (performFree) { FreeBlock(cacheList.LastItem(), sizeOfBlocksInCache, isMallocTest, theThread, &cacheList, &nonCacheList); } else { SaveBlock(theCache, cacheList.LastItem(), sizeOfBlocksInCache, theThread, &cacheList, &nonCacheList); } performFree = !performFree; } // Free or save (every other block) for all "non-cache sized" blocks. while (!nonCacheList.IsEmpty()) { if (performFree) { FreeBlock(nonCacheList.LastItem(), sizeOfNonCacheBlocks, isMallocTest, theThread, &cacheList, &nonCacheList); } else { SaveBlock(theCache, nonCacheList.LastItem(), sizeOfNonCacheBlocks, theThread, &cacheList, &nonCacheList); } performFree = !performFree; } } }
void DeleteSymbol(symtabADT table, string key) { symtabNodeT *np; np = DeleteBSTNode(table->bst, &key); if (np != NULL) { FreeBlock(np->key); FreeBlock(np); } }
void FreePQueue(pqueueADT pqueue) { cellT *next; while (pqueue->head != NULL) { next = pqueue->head->next; FreeBlock(pqueue->head); pqueue->head = next; } FreeBlock(pqueue); }
// Release the SSTP server void FreeSstpServer(SSTP_SERVER *s) { // Validate arguments if (s == NULL) { return; } TubeDisconnect(s->TubeRecv); TubeDisconnect(s->TubeSend); WaitThread(s->PPPThread, INFINITE); ReleaseThread(s->PPPThread); while (true) { BLOCK *b = GetNext(s->RecvQueue); if (b == NULL) { break; } FreeBlock(b); } while (true) { BLOCK *b = GetNext(s->SendQueue); if (b == NULL) { break; } FreeBlock(b); } ReleaseQueue(s->RecvQueue); ReleaseQueue(s->SendQueue); ReleaseSockEvent(s->SockEvent); FreeInterruptManager(s->Interrupt); ReleaseCedar(s->Cedar); ReleaseTube(s->TubeSend); ReleaseTube(s->TubeRecv); Free(s); }
static void SendQueuedMessages() { byte buf[MEMCOPY_THRESHOLD]; size_t dataLen; MemBlock * block; for (;;) { if (!gPipe) return; dataLen = 0; block = GetDataToSend(buf, dimof(buf), &dataLen); byte *dataToSend = buf; if (block) { dataToSend = block->UnsentData(); dataLen = block->UnsentLen(); } if (0 == dataLen) { CrashIf(block); return; } //lf("memtrace.dll: sending %d bytes", (int)dataLen); WriteToPipe(dataToSend, dataLen); if (block) { block->sent += dataLen; FreeBlock(block); } } }
// パケットアダプタの解放 void LinkPaFree(SESSION *s) { LINK *k; // 引数チェック if (s == NULL || (k = (LINK *)s->PacketAdapter->Param) == NULL) { return; } // サーバーセッションの停止 StopSession(k->ServerSession); ReleaseSession(k->ServerSession); // 送信パケットキューの解放 LockQueue(k->SendPacketQueue); { BLOCK *block; while (block = GetNext(k->SendPacketQueue)) { FreeBlock(block); } } UnlockQueue(k->SendPacketQueue); ReleaseQueue(k->SendPacketQueue); }
void BasicPQueueTest(void) { int i; pqueueADT pq; printf("\n----------- Testing Basic PQueue functions -----------\n\n"); pq = NewPQueue(); printf("The pqueue was just created. Is it empty? %s", IsEmpty(pq) ? "TRUE" : "FALSE"); for (i = 1; i <= 10; i++) Enqueue(pq, i); printf("\nEnqueuing the integers from 1 to 10 (in forward order)\n"); printf("Pqueue should not be empty. Is it empty? %s\n", IsEmpty(pq) ? "TRUE" : "FALSE"); printf("Dequeuing the top 5 elements: "); for (i = 0; i < 5; i++) printf("%d ", DequeueMax(pq)); printf("\nDequeuing all the rest: "); while (!IsEmpty(pq)) printf("%d ", DequeueMax(pq)); printf("\nPqueue should be empty. Is it empty? %s\n", IsEmpty(pq) ? "TRUE" : "FALSE"); FreePQueue(pq); printf("Hit return to continue: "); { string s = GetLine(); FreeBlock(s); } }
// Release the packet adapter void LinkPaFree(SESSION *s) { LINK *k; // Validate arguments if (s == NULL || (k = (LINK *)s->PacketAdapter->Param) == NULL) { return; } CedarAddQueueBudget(k->Cedar, -((int)k->LastServerConnectionReceivedBlocksNum)); k->LastServerConnectionReceivedBlocksNum = 0; // Stop the server session StopSession(k->ServerSession); ReleaseSession(k->ServerSession); // Release the transmission packet queue LockQueue(k->SendPacketQueue); { BLOCK *block; while (block = GetNext(k->SendPacketQueue)) { FreeBlock(block); } } UnlockQueue(k->SendPacketQueue); ReleaseQueue(k->SendPacketQueue); k->CurrentSendPacketQueueSize = 0; }
// Release the packet adapter void LinkPaFree(SESSION *s) { LINK *k; // Validate arguments if (s == NULL || (k = (LINK *)s->PacketAdapter->Param) == NULL) { return; } // Stop the server session StopSession(k->ServerSession); ReleaseSession(k->ServerSession); // Release the transmission packet queue LockQueue(k->SendPacketQueue); { BLOCK *block; while (block = GetNext(k->SendPacketQueue)) { FreeBlock(block); } } UnlockQueue(k->SendPacketQueue); ReleaseQueue(k->SendPacketQueue); }
// Release void NullPaFree(SESSION *s) { // Validate arguments NULL_LAN *n; BLOCK *b; if (s == NULL || (n = s->PacketAdapter->Param) == NULL) { return; } n->Halt = true; Set(n->Event); WaitThread(n->PacketGeneratorThread, INFINITE); ReleaseThread(n->PacketGeneratorThread); LockQueue(n->PacketQueue); { while (b = GetNext(n->PacketQueue)) { FreeBlock(b); } } UnlockQueue(n->PacketQueue); ReleaseQueue(n->PacketQueue); ReleaseCancel(n->Cancel); ReleaseEvent(n->Event); s->PacketAdapter->Param = NULL; Free(n); }
void DeleteFileFromDatabase(int fileno) { FILE *file = fopen("blob.bin", "rb+"); fseek(file, USERSOFFSET, SEEK_SET); struct UserData u; struct User user; fread(&u, sizeof(struct UserData), 1, file); user = u.users[CURRENT_USER]; int filesoffset = user.files_offset; struct FilesCollection f; struct File binfile; fseek(file, filesoffset, SEEK_SET); fread(&f, sizeof(struct FilesCollection), 1, file); binfile = f.files[fileno]; for (int i = fileno; i < f.files_count; i++) { f.files[i] = f.files[i + 1]; } f.files_count--; fseek(file, filesoffset, SEEK_SET); fwrite(&f, sizeof(struct FilesCollection), 1, file); int offset = binfile.offset; struct DataBlock d; while (offset>0) { fseek(file, offset, SEEK_SET); fread(&d, sizeof(struct DataBlock), 1, file); FreeBlock(offset); offset = d.nextoffset; } fclose(file); }
void MMMem::Free( const void *pAllocation ) { if( pAllocation ) { blockHeader *pBlockHdr = *((blockHeader**)(((uint32)pAllocation) - allocHeaderSize - sizeof(blockHeader*))); assert( pBlockHdr->pAlloc == pAllocation ); FreeBlock( pBlockHdr ); } }
void StormFixedBlockAllocator::FreeBlockChain(StormFixedBlockHandle handle, StormFixedBlockType::Index type) { StormFixedBlockHandle cur = handle; while (cur != InvalidBlockHandle) { cur = FreeBlock(cur, type); } }
afs_int32 ka_DelKey(struct ubik_trans *tt, afs_int32 tentryaddr, struct kaentry *tentry) { int code; struct kaOldKeys okeys; /* old keys block */ afs_int32 okeysaddr, nextaddr; /* offset of old keys block */ afs_int32 prevptr = 0; es_Report("DelKey for %s.%s\n", tentry->userID.name, tentry->userID.instance); /* An entry may have more than one oldkeys blocks. The entry * points to the most current, but all the oldkeys blocks for an * entry are not linked together. All oldkeys blocks for all * entries are linked together off of the header. So we follow * this link. */ for (okeysaddr = ntohl(cheader.kvnoPtr); okeysaddr; okeysaddr = nextaddr) { /* foreacholdkeysblock */ /* Read the oldKeys block */ code = karead(tt, okeysaddr, (char *)&okeys, sizeof(okeys)); if (code) return code; nextaddr = ntohl(okeys.next); /* We only want oldkey blocks that belong to this entry */ if (ntohl(okeys.entry) != tentryaddr) { prevptr = DOFFSET(okeysaddr, &okeys, &okeys.next); continue; } /* Delete the oldkeys block */ if (prevptr) { code = kawrite(tt, prevptr, (char *)&okeys.next, sizeof(afs_int32)); } else { code = set_header_word(tt, kvnoPtr, okeys.next); } if (code) return code; code = FreeBlock(tt, okeysaddr); if (code) return code; } /* foreacholdkeysblock */ /* Update the tentry. We rely on caller to write it out */ tentry->misc.asServer.oldKeys = 0; tentry->misc.asServer.nOldKeys = 0; /* invalidate key caches everywhere */ code = inc_header_word(tt, specialKeysVersion); if (code) return code; return 0; }
void FreeListADT(listADT l) { Position cp, next; cp = l -> next; while (cp != NULL) { next = cp -> next; free(cp); cp = next; } FreeBlock(l); }
void CodeTorrent::CleanData() { int i; if (identity == CT_SERVER) { for (i = 0; i < (int) data.size(); i++) { FreeBlock(data[i]); } data.clear(); } }
static IMG_VOID LayoutExecPredCfgFromCtrlDepGraph(PINTERMEDIATE_STATE psState, PCTRL_DEP_GRAPH psCtrlDepGraph, PCFG psCfg, PCODEBLOCK psCfgActualExitBlock) { PCODEBLOCK psPrevCfgEntryBlock = psCfg->psEntry; PCODEBLOCK psPrevCfgExitBlock = psCfg->psExit; PCODEBLOCK psPrevSubCfgExitBlock = NULL; PCODEBLOCK psSubCfgEntryBlock; PCODEBLOCK psSubCfgExitBlock; PUSC_LIST_ENTRY psListEntry; PCTRL_DEP_NODE_LISTENTRY psCtrlDepNodeLstEntry; for (psListEntry = psCtrlDepGraph->psRootCtrlDepNode->u.sBlock.apsSucc[0]->u.sRegion.sSuccLst.psHead; psListEntry != NULL; psListEntry = psListEntry->psNext) { psCtrlDepNodeLstEntry = IMG_CONTAINING_RECORD(psListEntry, PCTRL_DEP_NODE_LISTENTRY, sListEntry); LayoutCfgFromCtrlDepNode(psState, psCtrlDepNodeLstEntry->psCtrlDepNode, psCfg, &psSubCfgEntryBlock, &psSubCfgExitBlock, psCfgActualExitBlock, IMG_FALSE); if (psPrevSubCfgExitBlock == NULL) { psCfg->psEntry = psSubCfgEntryBlock; } else { SetBlockUnconditional(psState, psPrevSubCfgExitBlock, psSubCfgEntryBlock); } psPrevSubCfgExitBlock = psSubCfgExitBlock; } if(psCfgActualExitBlock == NULL) { psCfg->psExit = psPrevSubCfgExitBlock; } else { SetBlockUnconditional(psState, psPrevSubCfgExitBlock, psCfgActualExitBlock); psCfg->psExit = psCfgActualExitBlock; } FreeBlock(psState, psPrevCfgEntryBlock); ClearSuccessors(psState, psCfg->psExit); FreeBlock(psState, psPrevCfgExitBlock); psCfg->psExit->eType = CBTYPE_EXIT; psCfg->psEntry->psIDom = NULL; psCfg->pfnCurrentSortOrder = NULL; }
// Release the UDP acceleration function void FreeUdpAccel(UDP_ACCEL *a) { // Validate arguments if (a == NULL) { return; } while (true) { BLOCK *b = GetNext(a->RecvBlockQueue); if (b == NULL) { break; } FreeBlock(b); } ReleaseQueue(a->RecvBlockQueue); ReleaseSock(a->UdpSock); if (a->IsInCedarPortList) { LockList(a->Cedar->UdpPortList); { DelInt(a->Cedar->UdpPortList, a->MyPort); } UnlockList(a->Cedar->UdpPortList); } // Release of NAT-T related a->NatT_Halt = true; Set(a->NatT_HaltEvent); if (a->NatT_GetIpThread != NULL) { WaitThread(a->NatT_GetIpThread, INFINITE); ReleaseThread(a->NatT_GetIpThread); } ReleaseEvent(a->NatT_HaltEvent); DeleteLock(a->NatT_Lock); ReleaseCedar(a->Cedar); Free(a); }
static void ExpandStack(stackADT stack) { stackElementT *array; int i, newSize; newSize = stack->size*2; array = NewArray(newSize, stackElementT); for(i=0; i<stack->size; i++) array[i] = stack->elements[i]; FreeBlock (stack->elements); stack->elements = array; stack->size = newSize; }
double GetReal(void) { String line; double value; char termch; while (TRUE) { line = GetLine(); switch (sscanf(line, " %lf %c", &value, &termch)) { case 1: FreeBlock(line); return (value); case 2: printf("Unexpected character: '%c'\n", termch); break; default: printf("Please enter a real number\n"); break; } FreeBlock(line); printf("Retry: "); } }
static IMG_VOID OptimizeFunctionEnd(PINTERMEDIATE_STATE psState, PCODEBLOCK psReturnMergeTail) { IMG_UINT32 uPredIdx; for (uPredIdx = 0; uPredIdx < psReturnMergeTail->uNumPreds; uPredIdx++) { PCODEBLOCK psPredBlock = psReturnMergeTail->asPreds[uPredIdx].psDest; if (psPredBlock->psBody != NULL && psPredBlock->psBody->eOpcode == IRETURN) { OptimizeFunctionEnd(psState, psPredBlock); RedirectEdgesFromPredecessors(psState, psPredBlock, psReturnMergeTail, IMG_FALSE); ClearSuccessors(psState, psPredBlock); FreeBlock(psState, psPredBlock); } } }
/* ** Destroy the given Block after first unlinking it from the ** element list. Note that this unlinks the block from the ** element list only -- not from the block list. */ static void UnlinkAndFreeBlock(HtmlWidget *htmlPtr, HtmlBlock *pBlock){ if( pBlock->base.pNext ){ pBlock->base.pNext->base.pPrev = pBlock->base.pPrev; TestPoint(0); }else{ htmlPtr->pLast = pBlock->base.pPrev; TestPoint(0); } if( pBlock->base.pPrev ){ pBlock->base.pPrev->base.pNext = pBlock->base.pNext; TestPoint(0); }else{ htmlPtr->pFirst = pBlock->base.pNext; TestPoint(0); } pBlock->base.pPrev = pBlock->base.pNext = 0; FreeBlock(pBlock); }
void main (void) { worldADT world; int i; double time=InitialTimeInterval; int numcreature; speciesADT *speciesP; creatureADT *creatureP; while(TRUE) { Randomize(); InitGraphics(); InitWorldMap(NColumns,NRows); i=0; numcreature=0; world=NewWorld(NColumns,NRows); PrintInstructions1(); speciesP=SetSpecies(&numcreature); speciesP=Shuffle(speciesP,numcreature); creatureP=GetBlock( numcreature * sizeof (creatureADT) ); PlacingCreatures(world,creatureP,speciesP,numcreature); PrintInstructions2(); while ( !MouseButtonIsDown() || WantToContinue(creatureP,numcreature,&time) ) { TakeOneTurn(creatureP[i]); i=(i+1)%numcreature; Pause(time); } FreeWorld(world); FreeBlock(creatureP); if (!WantToPlayAgain()) {break;} } }
void PQueueSortTest(void) { int i; pqueueADT pq; int array[SORT_SIZE]; printf("\n----------- Testing use of pqueue to sort -----------\n"); pq = NewPQueue(); printf("Enqueuing %d numbers into pqueue in increasing order.", SORT_SIZE); for (i = 0; i < SORT_SIZE; i++) array[i] = i; HeapSort(pq, array, SORT_SIZE); printf("\nUsing dequeue to pull out numbers in sorted order. Are they sorted? %s\n", ArrayIsSorted(array, SORT_SIZE) ? "TRUE" : "FALSE"); printf("PQueue should be empty. Is it empty? %s\n", IsEmpty(pq) ? "TRUE" : "FALSE"); printf("\nEnqueuing %d numbers into pqueue in decreasing order.", SORT_SIZE); for (i = 0; i < SORT_SIZE; i++) array[i] = SORT_SIZE - i; HeapSort(pq, array, SORT_SIZE); printf("\nUsing dequeue to pull out numbers in sorted order. Are they sorted? %s\n", ArrayIsSorted(array, SORT_SIZE) ? "TRUE" : "FALSE"); printf("PQueue should be empty. Is it empty? %s\n", IsEmpty(pq) ? "TRUE" : "FALSE"); printf("\nEnqueuing %d random values into the pqueue.\n", SORT_SIZE); for (i = 0; i < SORT_SIZE; i++) array[i] = RandomInteger(1, 1000); HeapSort(pq, array, SORT_SIZE); printf("Using dequeue to pull out numbers in sorted order. Are they sorted? %s\n", ArrayIsSorted(array, SORT_SIZE) ? "TRUE" : "FALSE"); printf("PQueue should be empty. Is it empty? %s\n", IsEmpty(pq) ? "TRUE" : "FALSE"); printf("\nEnqueuing %d random possibly negative values into the pqueue.\n", SORT_SIZE); for (i = 0; i < SORT_SIZE; i++) array[i] = RandomInteger(-1000, 1000); HeapSort(pq, array, SORT_SIZE); printf("Using dequeue to pull out numbers in sorted order. Are they sorted? %s\n", ArrayIsSorted(array, SORT_SIZE) ? "TRUE" : "FALSE"); printf("PQueue should be empty. Is it empty? %s\n", IsEmpty(pq) ? "TRUE" : "FALSE"); FreePQueue(pq); printf("Hit return to continue: "); { string s = GetLine(); FreeBlock(s); } }
int freeOldBlockChain(struct ubik_trans *ut, dbadr diskAddr) { struct blockHeader blockHeader; dbadr nextDiskAddr; afs_int32 code = 0; while (diskAddr != 0) { /* read in the header */ code = dbread(ut, diskAddr, (char *)&blockHeader, sizeof(blockHeader)); if (code) ABORT(code); nextDiskAddr = ntohl(blockHeader.next); code = FreeBlock(ut, &blockHeader, diskAddr); if (code) ABORT(code); diskAddr = nextDiskAddr; } abort_exit: return (code); }
void MorePQueueTest(void) { int i; pqueueADT pq; printf("\n----------- More pqueue testing functions -----------\n"); pq = NewPQueue(); printf("\nEnqueuing the integers from 1 to 15 (in reverse order)\n"); for (i = 15; i > 0; i--) Enqueue(pq, i); printf("Enqueuing duplicates for evens from 2 to 14\n"); for (i = 2; i <= 14; i += 2) Enqueue(pq, i); printf("Dequeuing the top 10 elements: "); for (i = 0; i < 10; i++) printf("%d ", DequeueMax(pq)); printf("\nDequeuing all the rest: "); while (!IsEmpty(pq)) printf("%d ", DequeueMax(pq)); printf("\nPQueue should be empty. Is it empty? %s", IsEmpty(pq) ? "TRUE" : "FALSE"); printf("\nThis next test raises an error if your pqueue is working correctly.\n"); printf("Once you verify the test, comment it out to move on to the other tests.\n"); printf("(The test to comment out is line %d in the file %s).\n", __LINE__ + 1, __FILE__); //printf("Dequeue from empty pqueue returns %d", DequeueMax(pq)); FreePQueue(pq); printf("Hit return to continue: "); { string s = GetLine(); FreeBlock(s); } }
// encode a block from generation "gen" CodedBlockPtr SingleBlockEncoder::EncodeSingleBlock(int gen, int blockIdInGen, BlockPtr fragBlockData, int fragDataSize, int num_blocks_gen) { int block_size = fragDataSize; // int buffer_size = 2 * block_size; if(fragDataSize != block_size){ //TODO: Report error return NULL; } // create a new copy CodedBlockPtr cb_to = AllocCodedBlock(num_blocks_gen, block_size); cb_to->gen = gen; cb_to->num_blocks_gen = num_blocks_gen; cb_to->block_size = block_size; //Make a fake data to encode std::vector<BlockPtr> fakeData; BlockPtr pblk; for(int i=0;i<num_blocks_gen;i++){ pblk = AllocBlock((block_size)); memset(pblk, 0, (block_size)); if(i==blockIdInGen){ memcpy(pblk, fragBlockData, (block_size)); } fakeData.push_back(pblk); } nc->EncodeSingleBlock(fakeData, cb_to, blockIdInGen); //release fake data for(int i=0;i<(int) fakeData.size();i++){ FreeBlock(fakeData[i]); } fakeData.clear(); return cb_to; }
void CleanupEtherIPServer(ETHERIP_SERVER *s) { UINT i; // Validate arguments if (s == NULL) { return; } EtherIPLog(s, "LE_STOP"); if (s->IpcConnectThread != NULL) { ReleaseThread(s->IpcConnectThread); } if (s->Ipc != NULL) { FreeIPC(s->Ipc); } for (i = 0;i < LIST_NUM(s->SendPacketList);i++) { BLOCK *b = LIST_DATA(s->SendPacketList, i); FreeBlock(b); } ReleaseList(s->SendPacketList); ReleaseSockEvent(s->SockEvent); ReleaseCedar(s->Cedar); DeleteLock(s->Lock); Free(s); }
// Close adapter void CloseEth(ETH *e) { BLOCK *b; // Validate arguments if (e == NULL) { return; } ReleaseCancel(e->Cancel); if (e->SuAdapter != NULL) { // Close SeLow adapter SuCloseAdapter(e->SuAdapter); SuFree(e->Su); } else { // Close SEE adapter wp->PacketCloseAdapter(e->Adapter); wp->PacketFreePacket(e->Packet); wp->PacketFreePacket(e->PutPacket); } while (b = GetNext(e->PacketQueue)) { FreeBlock(b); } ReleaseQueue(e->PacketQueue); Free(e->Name); Free(e->Title); Free(e->Buffer); Free(e); }