axStatus axIString_<wchar_t> :: appendWithLength( const char *src, axSize src_len ) { if( ! src ) return 1; if( src_len <= 0 ) return 1; axSize req_len; axStatus st; st = ax_wchar_count_in_utf8( req_len, src, src_len ); if( !st ) return st; axSize old_size = size(); st = incSize( req_len ); if( !st ) return st; if( size() == 0 ) return 0; wchar_t* dst = &buf_[old_size]; int ret; axSize i; for( i=0; i < src_len; i++ ) { if( ! *src) return 0; ret = ax_utf8_to_wchar( *dst, src, src_len ); if( ret <= 0 ) { assert( false ); return -1; } dst ++; src += ret; } return 0; }
axStatus axIString_<wchar_t> :: insertWithLength( axSize pos, const char *src, axSize src_len ) { if( !src ) return 1; if( pos > size() ) return -1; axSize req_len; axStatus st; st = ax_wchar_count_in_utf8( req_len, src, src_len ); if( !st ) return st; if( req_len == 0 ) return 0; axSize old_size = size(); st = incSize( req_len ); if( !st ) return st; st = ax_array_take( &buf_[ pos+src_len ], &buf_[pos], old_size-pos ); if( !st ) return st; wchar_t *dst = &buf_[ pos ]; int ret; axSize i; for( i=0; i < src_len; i++ ) { if( ! *src ) return 0; ret = ax_utf8_to_wchar( *dst, src, src_len ); if( ret <= 0 ) { assert( false ); return -1; } dst++; src+=ret; } return 0; }
axStatus axIString_<char> :: append( wchar_t ch ) { axStatus st; axSize n; st = ax_utf8_count_in_wchar( n, ch ); if( !st ) return st; st = incSize( n ); if( !st ) return st; ax_wchar_to_utf8( &buf_.last(n), n, ch ); return 0; }
void incPosition(struct butm_tapeInfo *info, usd_handle_t fid, afs_uint32 dataSize) { /* Add this to the amount of data written to the tape */ incSize(info, dataSize); info->posCount += dataSize; if (info->posCount >= 2147467264) { /* 2GB - 16K */ info->posCount = 0; #if (defined(AFS_SUN_ENV) || defined(AFS_LINUX24_ENV)) if (!isafile) { afs_int64 off; off = 0; USD_IOCTL(fid, USD_IOCTL_SETSIZE, &off); } #endif } }
afs_int32 SeekFile(struct butm_tapeInfo *info, int count) { afs_int32 code = 0; struct progress *p; afs_int32 error = 0; if (count == 0) ERROR_EXIT(0); p = (struct progress *)info->tmRock; if (isafile) { /* no reason for seeking through a file */ p->reading = p->writing = 0; return (0); } POLL(); if (count > 0) error = ForwardSpace(p->fid, count); else error = BackwardSpace(p->fid, -count); POLL(); if (error) { info->status |= BUTM_STATUS_SEEKERROR; ERROR_EXIT(BUTM_IOCTL); } info->position += count; incSize(info, (count * config.fileMarkSize)); p = (struct progress *)info->tmRock; p->reading = p->writing = 0; error_exit: if (error) info->error = error; return (code); }
HashCollection::Elm& HashCollection::allocElmFront(MixedArray::Inserter ei) { assert(MixedArray::isValidIns(ei) && !MixedArray::isValidPos(*ei)); assert(m_size <= posLimit() && posLimit() < cap()); // Move the existing elements to make element slot 0 available. memmove(data() + 1, data(), posLimit() * sizeof(Elm)); incPosLimit(); // Update the hashtable to reflect the fact that everything was // moved over one position auto* hash = hashTab(); auto* hashEnd = hash + hashSize(); for (; hash != hashEnd; ++hash) { if (validPos(*hash)) { ++(*hash); } } // Set the hash entry we found to point to element slot 0. (*ei) = 0; // Adjust m_pos so that is points at this new first element. arrayData()->m_pos = 0; // Adjust size to reflect that we're adding a new element. incSize(); // Store the value into element slot 0. return data()[0]; }
static afs_int32 ReadTapeBlock(struct butm_tapeInfo *info, char *buffer, /* assumed to be 16384 bytes */ afs_int32 *blockType) { afs_int32 code = 0; afs_int32 rsize, fmtype; struct tapeLabel *label; struct fileMark *fmark; struct blockMark *bmark; struct progress *p; *blockType = BLOCK_UNKNOWN; p = (struct progress *)info->tmRock; memset(buffer, 0, BUTM_BLOCKSIZE); label = (struct tapeLabel *)buffer; fmark = (struct fileMark *)buffer; bmark = (struct blockMark *)buffer; rsize = readData(p->fid, buffer, BUTM_BLOCKSIZE, &info->error); if (rsize > 0) { incPosition(info, p->fid, rsize); p->reading++; } if (rsize == 0) { /* Read a HW EOF Marker? OK */ *blockType = BLOCK_EOF; incSize(info, config.fileMarkSize); /* Size of filemark */ if (!isafile) info->position++; /* bump position */ p->reading = 0; /* No reads since EOF */ } else if (rsize != BUTM_BLOCKSIZE) { /* Didn't Read a full block */ info->status |= BUTM_STATUS_READERROR; ERROR_EXIT((rsize < 0) ? BUTM_IO : BUTM_EOT); } else if (ntohl(bmark->magic) == BLOCK_MAGIC) { /* Data block? */ *blockType = BLOCK_DATA; } else if (ntohl(fmark->magic) == FILE_MAGIC) { /* Read a filemark? */ fmtype = ntohl(fmark->nBytes); if (fmtype == FILE_BEGIN) { /* filemark begin */ *blockType = BLOCK_FMBEGIN; } else if (fmtype == FILE_FMEND) { /* filemark end */ *blockType = BLOCK_FMEND; code = SeekFile(info, 1); } else if (fmtype == FILE_EOD) { /* EOD mark */ *blockType = BLOCK_EOD; info->status |= BUTM_STATUS_EOD; code = SeekFile(info, 1); } } else if (ntohl(label->magic) == TAPE_MAGIC) { /* Read a tape label? */ *blockType = BLOCK_LABEL; code = SeekFile(info, 1); } if (isafile) info->position++; error_exit: return (code); }
static afs_int32 WriteTapeBlock(struct butm_tapeInfo *info, char *buffer, /* assumed to be 16384 bytes with data in it */ afs_int32 length, /* amount data in buffer */ afs_int32 blockType) { afs_int32 code = 0, rc = 0; afs_uint32 wsize; struct tapeLabel *label; struct fileMark *fmark; struct blockMark *bmark; struct progress *p; afs_int32 error = 0; p = (struct progress *)info->tmRock; if (blockType == BLOCK_DATA) { /* Data Block */ if (length == 0) ERROR_EXIT(0); bmark = (struct blockMark *)buffer; memset(bmark, 0, sizeof(struct blockMark)); bmark->magic = htonl(BLOCK_MAGIC); bmark->count = htonl(length); } else if (blockType == BLOCK_FMBEGIN) { /* Filemark - begin */ fmark = (struct fileMark *)buffer; fmark->magic = htonl(FILE_MAGIC); fmark->nBytes = htonl(FILE_BEGIN); } else if (blockType == BLOCK_FMEND) { /* Filemark - end */ fmark = (struct fileMark *)buffer; fmark->magic = htonl(FILE_MAGIC); fmark->nBytes = htonl(FILE_FMEND); } else if (blockType == BLOCK_LABEL) { /* Label */ label = (struct tapeLabel *)buffer; label->magic = htonl(TAPE_MAGIC); } else if (blockType == BLOCK_EOD) { /* Filemark - EOD mark */ fmark = (struct fileMark *)buffer; fmark->magic = htonl(FILE_MAGIC); fmark->nBytes = htonl(FILE_EOD); } /* Write the tape block */ /* -------------------- */ rc = USD_WRITE(p->fid, buffer, BUTM_BLOCKSIZE, &wsize); if ((rc == 0) && (wsize > 0)) { incPosition(info, p->fid, wsize); /* record whats written */ p->writing++; } if (wsize != BUTM_BLOCKSIZE) { info->status |= BUTM_STATUS_WRITEERROR; if (rc != 0) { error = rc; ERROR_EXIT(BUTM_IO); } else ERROR_EXIT(BUTM_EOT); } if (isafile) info->position++; /* Write trailing EOF marker for some block types */ /* ---------------------------------------------- */ if ((blockType == BLOCK_FMEND) || (blockType == BLOCK_LABEL) || (blockType == BLOCK_EOD)) { POLL(); error = WriteEOF(p->fid, 1); POLL(); if (error) { info->status |= BUTM_STATUS_WRITEERROR; ERROR_EXIT(BUTM_IOCTL); } incSize(info, config.fileMarkSize); if (!isafile) info->position++; p->writing = 0; } error_exit: if (error) info->error = error; return (code); }
axStatus axIString_<char> :: append( char ch ) { axStatus st; st = incSize( 1 ); if( !st ) return st; buf_.last(1) = ch; return 0; }
Address RecordManager::insertRecord(vector<char>& newRecord, string fileName, int recordSize){ Address addr(fileName, 0, 0); Address head(fileName, 0, 0);//head vector<char> headRecord; vector<char> nextBlock; vector<char> nextOffset; int newBlock; int newOffset; int headSize; if (recordSize < 20) headSize = 20; else headSize = recordSize; ///////文件中无记录/////// if (bmanager.getFileBlockNumber(fileName) == 0){ bmanager.createFile(fileName); //清空文件头 newHead(headRecord, headSize); //新纪录位置(0,1) newBlock = 0; newOffset = headSize; //新纪录指向head(不用改了,default) } else{ headRecord = bmanager.read(head, headSize); int size = getSize(headRecord); if (size == 0){ //清空文件头 newHead(headRecord, headSize); //新纪录位置(0,1) newBlock = 0; newOffset = headSize; //新纪录指向head(不用改了,default) } ///////文件中有记录/////// else{ //新纪录位置 setNextAddr(headRecord, nextBlock, nextOffset, headSize- 16);//第一条被删的记录 int delBlock = char4ToInt(nextBlock); int delOffset = char4ToInt(nextOffset); if (delBlock == 0 && delOffset == 0){//没有被删记录 int n;//一块中的记录数 int block = bmanager.getFileBlockNumber(fileName) - 1; int offset; int size = getSize(headRecord);//文件中的记录数(不包括head) if (block == 0){ n = (4096 - headSize) / recordSize;//第一块中的record数 if (size == n){ newBlock = block + 1; newOffset = 0; } else{//size<n newBlock = block; newOffset = headSize + (size%n)*recordSize; } } else{ n = 4096 / recordSize;//其他块中最多能放的record数 if (size == (4096 - headSize) / recordSize+block*n){ newBlock = block + 1; newOffset = 0; } else{ newBlock = block; newOffset = ((size - (4096 - headSize) / recordSize) % n)*recordSize; } } } else{///有被删记录 //空位在(delBlock,delOffset) newBlock = delBlock; newOffset = delOffset; //修改文件头中的del指针,使它指向第二条被删记录 addr.setAddr(fileName, delBlock, delOffset); vector<char> tempRecord = bmanager.read(addr, recordSize); setNextAddr(tempRecord, nextBlock, nextOffset, recordSize - 8); updateRecordPoint(headRecord, nextBlock, nextOffset, headSize - 16); } //newRecord指向第一条记录 setNextAddr(headRecord, nextBlock, nextOffset, headSize - 8); updateRecordPoint(newRecord, nextBlock, nextOffset, recordSize - 8); } } //插入新记录 addr.setAddr(fileName, newBlock, newOffset); bmanager.write(addr, newRecord);//√ //更新head //head指向第一条记录 intToChar4(newBlock, nextBlock); intToChar4(newOffset, nextOffset); updateRecordPoint(headRecord, nextBlock, nextOffset, headSize - 8); //更新head中的size incSize(headRecord); //写回headRecord bmanager.write(head, headRecord);//√ return addr; }
void append(const hsTArray<T>& items) { size_t ins = getSize(); incSize(items.getSize()); for (size_t i=0; i<items.getSize(); i++) data[ins + i] = items.get(i); }
void append(const T& item) { incSize(); data[count - 1] = item; }
ALWAYS_INLINE typename std::enable_if< std::is_base_of<BaseMap, TMap>::value, Object>::type BaseMap::php_map(const Variant& callback) const { VMRegGuard _; CallCtx ctx; vm_decode_function(callback, nullptr, false, ctx); if (!ctx.func) { SystemLib::throwInvalidArgumentExceptionObject( "Parameter must be a valid callback"); } auto map = req::make<TMap>(); if (!m_size) return Object{std::move(map)}; assert(posLimit() != 0); assert(hashSize() > 0); assert(map->arrayData() == staticEmptyMixedArray()); map->m_arr = MixedArray::asMixed(MixedArray::MakeReserveMixed(cap())); map->setIntLikeStrKeys(intLikeStrKeys()); wordcpy(map->hashTab(), hashTab(), hashSize()); { uint32_t used = posLimit(); int32_t version = m_version; uint32_t i = 0; // When the loop below finishes or when an exception is thrown, // make sure that posLimit() get set to the correct value and // that m_pos gets set to point to the first element. SCOPE_EXIT { map->setPosLimit(i); map->arrayData()->m_pos = map->nthElmPos(0); }; constexpr int64_t argc = useKey ? 2 : 1; TypedValue argv[argc]; for (; i < used; ++i) { const Elm& e = data()[i]; Elm& ne = map->data()[i]; if (isTombstone(i)) { ne.data.m_type = e.data.m_type; continue; } TypedValue* tv = &ne.data; if (useKey) { if (e.hasIntKey()) { argv[0].m_type = KindOfInt64; argv[0].m_data.num = e.ikey; } else { argv[0].m_type = KindOfString; argv[0].m_data.pstr = e.skey; } } argv[argc-1] = e.data; g_context->invokeFuncFew(tv, ctx, argc, argv); if (UNLIKELY(version != m_version)) { tvRefcountedDecRef(tv); throw_collection_modified(); } if (e.hasStrKey()) { e.skey->incRefCount(); } ne.ikey = e.ikey; ne.data.hash() = e.data.hash(); map->incSize(); // Needed so that the new elements are accounted for when GC scanning. map->incPosLimit(); } } return Object{std::move(map)}; }