当前位置: 首页>>代码示例>>C++>>正文


C++ BPositionIO类代码示例

本文整理汇总了C++中BPositionIO的典型用法代码示例。如果您正苦于以下问题:C++ BPositionIO类的具体用法?C++ BPositionIO怎么用?C++ BPositionIO使用的例子?那么, 这里精选的类代码示例或许可以为您提供帮助。


在下文中一共展示了BPositionIO类的13个代码示例,这些例子默认根据受欢迎程度排序。您可以为喜欢或者感觉有用的代码点赞,您的评价将有助于系统推荐出更棒的C++代码示例。

示例1: TRACE_IO

/*static*/ off_t
AVFormatWriter::_Seek(void* cookie, off_t offset, int whence)
{
	TRACE_IO("AVFormatWriter::_Seek(%p, %lld, %d)\n",
		cookie, offset, whence);

	AVFormatWriter* writer = reinterpret_cast<AVFormatWriter*>(cookie);

	BPositionIO* positionIO = dynamic_cast<BPositionIO*>(writer->fTarget);
	if (positionIO == NULL)
		return -1;

	// Support for special file size retrieval API without seeking anywhere:
	if (whence == AVSEEK_SIZE) {
		off_t size;
		if (positionIO->GetSize(&size) == B_OK)
			return size;
		return -1;
	}

	off_t position = positionIO->Seek(offset, whence);
	TRACE_IO("  position: %lld\n", position);
	if (position < 0)
		return -1;

	return position;
}
开发者ID:luciang,项目名称:haiku,代码行数:27,代码来源:AVFormatWriter.cpp

示例2: new

/*static*/ status_t
FSUtils::CompareFileContent(BPositionIO& content1, BPositionIO& content2,
                            bool& _equal)
{
    // get and compare content size
    off_t size1;
    status_t error = content1.GetSize(&size1);
    if (error != B_OK)
        return error;

    off_t size2;
    error = content2.GetSize(&size2);
    if (error != B_OK)
        return error;

    if (size1 != size2) {
        _equal = false;
        return B_OK;
    }

    if (size1 == 0) {
        _equal = true;
        return B_OK;
    }

    // allocate a data buffer
    uint8* buffer1 = new(std::nothrow) uint8[2 * kCompareDataBufferSize];
    if (buffer1 == NULL)
        return B_NO_MEMORY;
    ArrayDeleter<uint8> bufferDeleter(buffer1);
    uint8* buffer2 = buffer1 + kCompareDataBufferSize;

    // compare the data
    off_t offset = 0;
    while (offset < size1) {
        size_t toCompare = std::min(size_t(size1 - offset),
                                    kCompareDataBufferSize);
        ssize_t bytesRead = content1.ReadAt(offset, buffer1, toCompare);
        if (bytesRead < 0)
            return bytesRead;
        if ((size_t)bytesRead != toCompare)
            return B_ERROR;

        bytesRead = content2.ReadAt(offset, buffer2, toCompare);
        if (bytesRead < 0)
            return bytesRead;
        if ((size_t)bytesRead != toCompare)
            return B_ERROR;

        if (memcmp(buffer1, buffer2, toCompare) != 0) {
            _equal = false;
            return B_OK;
        }

        offset += bytesRead;
    }

    _equal = true;
    return B_OK;
}
开发者ID:yunxiaoxiao110,项目名称:haiku,代码行数:60,代码来源:FSUtils.cpp

示例3:

/* static */ int
WebPTranslator::_EncodedWriter(const uint8_t* data, size_t dataSize,
	const WebPPicture* const picture)
{
	BPositionIO* target = (BPositionIO*)picture->custom_ptr;
	return dataSize ? (target->Write(data, dataSize) == (ssize_t)dataSize) : 1;
}
开发者ID:veer77,项目名称:Haiku-services-branch,代码行数:7,代码来源:WebPTranslator.cpp

示例4:

void
TiffUintField::LoadByte(IFDEntry &entry, BPositionIO &io, swap_action swp)
{
	// Make certain there is enough memory
	// before trying to do anything else
	fpByte = new uint8[entry.count];
	if (!fpByte) {
		finitStatus = B_NO_MEMORY;
		return;
	}
	
	if (entry.count <= 4) {
		// If all of the byte values can fit into the
		// IFD entry value bytes
		memcpy(fpByte, entry.bytevals, entry.count);
		finitStatus = B_OK;		
	} else {
	
		// entry.count > 4, use longval to find offset for byte data
		if (swap_data(B_UINT32_TYPE, &entry.longval, 4, swp) != B_OK)
			finitStatus = B_ERROR;
		else {
			ssize_t read;
			read = io.ReadAt(entry.longval, fpByte, entry.count);
			if (read != static_cast<ssize_t>(entry.count))
				finitStatus = B_IO_ERROR;
			else
				finitStatus = B_OK;
		}
		
	}
}
开发者ID:Ithamar,项目名称:cosmoe,代码行数:32,代码来源:TiffUintField.cpp

示例5: ReadStreamInfo

status_t 
MusePackReader::Sniff(int32 *_streamCount)
{
	BPositionIO *file = dynamic_cast<BPositionIO *>(Source());
	if (file == NULL)
		// we cannot handle non seekable files for now
		return B_ERROR;

	file->Seek(0, SEEK_SET);
	int error = fInfo.ReadStreamInfo(file);
	if (error > B_OK) {
		// error came from engine
		TRACE("MusePackReader: ReadStreamInfo() engine error %d\n", error);
		return B_ERROR;
	} else if (error < B_OK)
		return error;

	TRACE("MusePackReader: recognized MPC file\n");
	*_streamCount = 1;
	return B_OK;
}
开发者ID:skarmiglione,项目名称:haiku,代码行数:21,代码来源:MusePackReader.cpp

示例6: read_exactly

// read_exactly
static
void
read_exactly(BPositionIO& file, off_t position, void* buffer, size_t size,
			 const char* errorMessage = NULL)
{
	ssize_t read = file.ReadAt(position, buffer, size);
	if (read < 0)
		throw Exception(read, errorMessage);
	else if ((size_t)read != size) {
		if (errorMessage) {
			throw Exception("%s Read to few bytes (%ld/%lu).", errorMessage,
							read, size);
		} else
			throw Exception("Read to few bytes (%ld/%lu).", read, size);
	}
}
开发者ID:looncraz,项目名称:haiku,代码行数:17,代码来源:ResourceFile.cpp

示例7: get_seekable

static BPositionIO *
get_seekable(BDataIO * data)
{
	// try to cast to BPositionIO then perform a series of
	// sanity checks to ensure that seeking is reliable
	BPositionIO * seekable = dynamic_cast<BPositionIO *>(data);
	if (seekable == 0) {
		return 0;
	}
	// first try to get our current location
	off_t current = seekable->Seek(0, SEEK_CUR);
	if (current < 0) {
		return 0;
	}
	// check it against position
	if (current != seekable->Position()) {
		return 0;
	}
	// next try to seek to our current location (absolutely)
	if (seekable->Seek(current, SEEK_SET) < 0) {
		return 0;
	}
	// next try to seek to the start of the stream (absolutely)
	if (seekable->Seek(0, SEEK_SET) < 0) {
		return 0;
	}
	// then seek back to where we started
	if (seekable->Seek(current, SEEK_SET) < 0) {
		// really screwed
		return 0;
	}
	// next try to seek to the end of the stream (absolutely)
	if (seekable->Seek(0, SEEK_END) < 0) {
		return 0;
	}
	// then seek back to where we started
	if (seekable->Seek(current, SEEK_SET) < 0) {
		// really screwed
		return 0;
	}
	return seekable;
}
开发者ID:mariuz,项目名称:haiku,代码行数:42,代码来源:OggReaderPlugin.cpp

示例8: readfoldedline

_EXPORT ssize_t readfoldedline(BPositionIO &in, char **buffer, size_t *buflen)
{
	ssize_t len = buflen && *buflen ? *buflen : 0;
	char * buf = buffer && *buffer ? *buffer : NULL;
	ssize_t cnt = 0; // Number of characters currently in the buffer.
	char c;
	status_t errorCode;

	while (true)
	{
		// Make sure there is space in the buffer for two more characters (one
		// for the next character, and one for the end of string NUL byte).
		if (buf == NULL || cnt + 2 >= len)
		{
			char *temp = (char *)realloc(buf, len + 64);
			if (temp == NULL) {
				// Out of memory, however existing buffer remains allocated.
				cnt = ENOMEM;
				break;
			}
			len += 64;
			buf = temp;
		}

		errorCode = in.Read (&c,1); // A really slow way of reading - unbuffered.
		if (errorCode != 1) {
			if (errorCode < 0) {
				cnt = errorCode; // IO error encountered, just return the code.
			} else {
				// Really is end of file.  Also make it end of line if there is
				// some text already read in.  If the first thing read was EOF,
				// just return an empty string.
				if (cnt > 0) {
					buf[cnt++] = '\n';
					if (buf[cnt-2] == '\r') {
						buf[cnt-2] = '\n';
						--cnt;
					}
				}
			}
			break;
		}

		buf[cnt++] = c;

		if (c == '\n') {
			// Convert CRLF end of line to just a LF.  Do it before folding, in
			// case we don't need to fold.
			if (cnt >= 2 && buf[cnt-2] == '\r') {
				buf[cnt-2] = '\n';
				--cnt;
			}
			// If the current line is empty then return it (so that empty lines
			// don't disappear if the next line starts with a space).
			if (cnt <= 1)
				break;
			// if first character on the next line is whitespace, fold lines
			errorCode = in.Read(&c,1);
			if (errorCode == 1) {
				if (c == ' ' || c == '\t')
					buf[cnt-1] = c; // Replace \n with the white space character.
				else {
					// Not folding, we finished reading a whole line.
					in.Seek(-1,SEEK_CUR); // Undo the look-ahead character read.
					break;
				}
			} else if (errorCode < 0) {
				cnt = errorCode;
				break;
			} else // No next line; at the end of the file.  Return the line.
				break;
		}
	}

	if (buf != NULL && cnt >= 0)
		buf[cnt] = '\0';

	if (buffer)
		*buffer = buf;
	else if (buf)
		free(buf);

	if (buflen)
		*buflen = len;

	return cnt;
}
开发者ID:HaikuArchives,项目名称:BeMailDaemon,代码行数:87,代码来源:mail_util.cpp

示例9: _EmitDebug

void
BHttpRequest::_SendPostData()
{
	if (fRequestMethod == B_HTTP_POST && fOptPostFields != NULL) {
		if (fOptPostFields->GetFormType() != B_HTTP_FORM_MULTIPART) {
			BString outputBuffer = fOptPostFields->RawData();
			_EmitDebug(B_URL_PROTOCOL_DEBUG_TRANSFER_OUT,
				"%s", outputBuffer.String());
			fSocket->Write(outputBuffer.String(), outputBuffer.Length());
		} else {
			for (BHttpForm::Iterator it = fOptPostFields->GetIterator();
				const BHttpFormData* currentField = it.Next();
				) {
				_EmitDebug(B_URL_PROTOCOL_DEBUG_TRANSFER_OUT,
					it.MultipartHeader().String());
				fSocket->Write(it.MultipartHeader().String(),
					it.MultipartHeader().Length());

				switch (currentField->Type()) {
					default:
					case B_HTTPFORM_UNKNOWN:
						ASSERT(0);
						break;

					case B_HTTPFORM_STRING:
						fSocket->Write(currentField->String().String(),
							currentField->String().Length());
						break;

					case B_HTTPFORM_FILE:
						{
							BFile upFile(currentField->File().Path(),
								B_READ_ONLY);
							char readBuffer[kHttpBufferSize];
							ssize_t readSize;

							readSize = upFile.Read(readBuffer,
								sizeof(readBuffer));
							while (readSize > 0) {
								fSocket->Write(readBuffer, readSize);
								readSize = upFile.Read(readBuffer,
									sizeof(readBuffer));
							}

							break;
						}
					case B_HTTPFORM_BUFFER:
						fSocket->Write(currentField->Buffer(),
							currentField->BufferSize());
						break;
				}

				fSocket->Write("\r\n", 2);
			}

			BString footer = fOptPostFields->GetMultipartFooter();
			fSocket->Write(footer.String(), footer.Length());
		}
	} else if ((fRequestMethod == B_HTTP_POST || fRequestMethod == B_HTTP_PUT)
		&& fOptInputData != NULL) {

		// If the input data is seekable, we rewind it for each new request.
		BPositionIO* seekableData
			= dynamic_cast<BPositionIO*>(fOptInputData);
		if (seekableData)
			seekableData->Seek(0, SEEK_SET);

		for (;;) {
			char outputTempBuffer[kHttpBufferSize];
			ssize_t read = fOptInputData->Read(outputTempBuffer,
				sizeof(outputTempBuffer));

			if (read <= 0)
				break;

			if (fOptInputDataSize < 0) {
				// Chunked transfer
				char hexSize[16];
				size_t hexLength = sprintf(hexSize, "%ld", read);

				fSocket->Write(hexSize, hexLength);
				fSocket->Write("\r\n", 2);
				fSocket->Write(outputTempBuffer, read);
				fSocket->Write("\r\n", 2);
			} else {
				fSocket->Write(outputTempBuffer, read);
			}
		}

		if (fOptInputDataSize < 0) {
			// Chunked transfer terminating sequence
			fSocket->Write("0\r\n\r\n", 5);
		}
	}

}
开发者ID:SummerSnail2014,项目名称:haiku,代码行数:96,代码来源:HttpRequest.cpp

示例10: convert_data_to_bits

static status_t
convert_data_to_bits(pcx_header &header, StreamBuffer &source,
	BPositionIO &target)
{
	uint16 bitsPerPixel = header.bitsPerPixel;
	uint16 bytesPerLine = header.bytesPerLine;
	uint32 width = header.xMax - header.xMin + 1;
	uint32 height = header.yMax - header.yMin + 1;
	uint16 numPlanes = header.numPlanes;
	uint32 scanLineLength = numPlanes * bytesPerLine;

	// allocate buffers
	TempAllocator scanLineAllocator;
	TempAllocator paletteAllocator;
	uint8 *scanLineData[height];
	uint8 *palette = (uint8 *)paletteAllocator.Allocate(3 * 256);
	status_t status = B_OK;

	for (uint32 row = 0; row < height; row++) {
		TRACE("scanline %ld\n", row);
		scanLineData[row] = (uint8 *)scanLineAllocator.Allocate(scanLineLength);
		if (scanLineData[row] == NULL)
			return B_NO_MEMORY;
		uint8 *line = scanLineData[row];
		uint32 index = 0;
		uint8 x;
		do {
			if (source.Read(&x, 1) != 1) {
				status = B_IO_ERROR;
				break;
			}
			if ((x & 0xc0) == 0xc0) {
				uint32 count = x & 0x3f;
				if (index + count - 1 > scanLineLength) {
					status = B_BAD_DATA;
					break;
				}
				if (source.Read(&x, 1) != 1) {
					status = B_IO_ERROR;
					break;
				}
				for (uint32 i = 0; i < count; i++)
					line[index++] = x;
			} else {
				line[index++] = x;
			}
		} while (index < scanLineLength);

		if (status != B_OK) {
			// If we've already read more than a third of the file, display
			// what we have, ie. ignore the error.
			if (row < height / 3)
				return status;

			memset(scanLineData + row, 0, sizeof(uint8*) * (height - row));
			break;
		}
	}

	if (bitsPerPixel == 8 && numPlanes == 1) {
		TRACE("palette reading %p 8\n", palette);
		uint8 x;
		if (status != B_OK || source.Read(&x, 1) != 1 || x != 12) {
			// Try again by repositioning the file stream
			if (source.Seek(-3 * 256 - 1, SEEK_END) < 0)
				return B_BAD_DATA;
			if (source.Read(&x, 1) != 1)
				return B_IO_ERROR;
			if (x != 12)
				return B_BAD_DATA;
		}
		if (source.Read(palette, 256 * 3) != 256 * 3)
			return B_IO_ERROR;
	} else {
		TRACE("palette reading %p palette\n", palette);
		memcpy(palette, &header.paletteInfo, 48);
	}

	uint8 alpha = 255;
	if (bitsPerPixel == 1 && numPlanes == 1) {
		TRACE("target writing 1\n");
		palette[0] = palette[1] = palette[2] = 0;
		palette[3] = palette[4] = palette[5] = 0xff;
		for (uint32 row = 0; row < height; row++) {
			uint8 *line = scanLineData[row];
			if (line == NULL)
				break;
			uint8 mask[] = { 128, 64, 32, 16, 8, 4, 2, 1 };
			for (uint32 i = 0; i < width; i++) {
				bool isBit = ((line[i >> 3] & mask[i & 7]) != 0) ? true : false;
				target.Write(&palette[!isBit ? 2 : 5], 1);
				target.Write(&palette[!isBit ? 1 : 4], 1);
				target.Write(&palette[!isBit ? 0 : 3], 1);
				target.Write(&alpha, 1);
			}
		}
	} else if (bitsPerPixel == 4 && numPlanes == 1) {
开发者ID:AmirAbrams,项目名称:haiku,代码行数:97,代码来源:PCX.cpp

示例11: Read

void CCellView::Read(BPositionIO& stream)
{
	CSwapStream str(stream);

	scChunk chunk;
	long offset;
	int *funcList, *styleList, *fontList, *formatList;
	int funcCount, styleCount, fontCount, formatCount, borderFont = fBorderFontID;
	bool warnForIncorrectFormula = true;
	scCell cl;

	styleCount = 0;
	styleList = (int *)MALLOC(0);
	fontCount = 0;
	fontList = (int *)MALLOC(0);
	formatCount = 0;
	formatList = (int *)MALLOC(0);
	funcList = NULL;
	
	scCSElement *colStyles = NULL;
	int colStyleCount = 0;

	offset = 0;

	StProgress progress(this, 1, pColorYellow, false);
	StWriteLock lock(fContainer);

	try
	{
		stream.Seek(offset, SEEK_SET);
		
		str >> chunk;

		if (chunk.type == kscVersion)
		{
			scVersion vers;
			str >> vers;
			if (vers.major != 3)
				THROW((errTooNewFileFormat));
		}
		else
			THROW((errUnknownFileFormat, ((CCellWindow *)Window())->EntryRef()->name));

		do
		{
			if (stream.Seek(offset, SEEK_SET) < offset)
			{
				MStopAlert("File is too short").Go();
				break;
			}
			
			str >> chunk;
			offset += 4 + chunk.size;
			
			switch (chunk.type)
			{
				case kscVersion:
					break;
				case kscHeader:
				{
					scHeader head;
					str >> head;
					
					funcList = (int *)CALLOC(head.functionCount, sizeof(int));
					FailNil(funcList);
					funcCount = head.functionCount;
					progress.NewMax(head.cellCount);
					break;
				}
				case kscView:
				{
					scView view;
					str >> view;
					
					if (view.windowRect.left > 0 && view.windowRect.top > 0)
					{
						BRect r;
						{
							r = BScreen().Frame();
						}

						r.InsetBy(4, 4);
						r = r & view.windowRect;
						
						if (r.IsValid() && r.Width() >= 300 && r.Height() >= 100)
						{
							Window()->MoveTo(r.left, r.top);
							Window()->ResizeTo(r.Width(), r.Height());
						}
					}
					if (view.position.h > 0 && view.position.v > 0)
						fPosition = view.position;
					fFrozen = view.frozen;
					if (view.selection.IsValid())
						fSelection = view.selection;
					if (fSelection.Contains(view.curCell))
						fCurCell = view.curCell;
					borderFont = view.headingFont;
					fShowGrid = (view.flags & kscShowGrid) != 0;
					fShowBorders = (view.flags & kscShowHeadings) != 0;
//.........这里部分代码省略.........
开发者ID:ModeenF,项目名称:OpenSumIt,代码行数:101,代码来源:CellView.IO.cpp

示例12: if

status_t
AGMSBayesianSpamFilter::ProcessMailMessage (
	BPositionIO** io_message,
	BEntry* io_entry,
	BMessage* io_headers,
	BPath* io_folder,
	const char* io_uid)
{
	ssize_t		 amountRead;
	attr_info	 attributeInfo;
	const char	*classificationString;
	off_t		 dataSize;
	BPositionIO	*dataStreamPntr = *io_message;
	status_t	 errorCode = B_OK;
	int32        headerLength;
	BString      headerString;
	BString		 newSubjectString;
	BNode        nodeForOutputFile;
	bool		 nodeForOutputFileInitialised = false;
	const char	*oldSubjectStringPntr;
	char         percentageString [30];
	BMessage	 replyMessage;
	BMessage	 scriptingMessage;
	team_id		 serverTeam;
	float		 spamRatio;
	char		*stringBuffer = NULL;
	char         tempChar;
	status_t     tempErrorCode;
	const char  *tokenizeModeStringPntr;

	// Set up a BNode to the final output file so that we can write custom
	// attributes to it.  Non-custom attributes are stored separately in
	// io_headers.

	if (io_entry != NULL && B_OK == nodeForOutputFile.SetTo (io_entry))
		nodeForOutputFileInitialised = true;

	// Get a connection to the spam database server.  Launch if needed, should
	// only need it once, unless another e-mail thread shuts down the server
	// inbetween messages.  This code used to be in InitCheck, but apparently
	// that isn't called.

	printf("Checking for Spam Server.\n");
	if (fLaunchAttemptCount == 0 || !fMessengerToServer.IsValid ()) {
		if (fLaunchAttemptCount > 3)
			goto ErrorExit; // Don't try to start the server too many times.
		fLaunchAttemptCount++;

		// Make sure the server is running.
		if (!be_roster->IsRunning (kServerSignature)) {
			errorCode = be_roster->Launch (kServerSignature);
			if (errorCode != B_OK) {
				BPath path;
				entry_ref ref;
				directory_which places[] = {B_COMMON_BIN_DIRECTORY,B_BEOS_BIN_DIRECTORY};
				for (int32 i = 0; i < 2; i++) {
					find_directory(places[i],&path);
					path.Append("spamdbm");
					if (!BEntry(path.Path()).Exists())
						continue;
					get_ref_for_path(path.Path(),&ref);
					if ((errorCode =  be_roster->Launch (&ref)) == B_OK)
						break;
				}
				if (errorCode != B_OK)
					goto ErrorExit;
			}
		}

		// Set up the messenger to the database server.
		serverTeam = be_roster->TeamFor (kServerSignature);
		if (serverTeam < 0)
			goto ErrorExit;
		fMessengerToServer =
			BMessenger (kServerSignature, serverTeam, &errorCode);
		if (!fMessengerToServer.IsValid ())
			goto ErrorExit;

		// Check if the server is running in headers only mode.  If so, we only
		// need to download the header rather than the entire message.
		scriptingMessage.MakeEmpty ();
		scriptingMessage.what = B_GET_PROPERTY;
		scriptingMessage.AddSpecifier ("TokenizeMode");
		replyMessage.MakeEmpty ();
		if ((errorCode = fMessengerToServer.SendMessage (&scriptingMessage,
			&replyMessage)) != B_OK)
			goto ErrorExit;
		if ((errorCode = replyMessage.FindInt32 ("error", &tempErrorCode))
			!= B_OK)
			goto ErrorExit;
		if ((errorCode = tempErrorCode) != B_OK)
			goto ErrorExit;
		if ((errorCode = replyMessage.FindString ("result",
			&tokenizeModeStringPntr)) != B_OK)
			goto ErrorExit;
		fHeaderOnly = (tokenizeModeStringPntr != NULL
			&& strcmp (tokenizeModeStringPntr, "JustHeader") == 0);
	}

	// See if the message has already been classified.  Happens for messages
//.........这里部分代码省略.........
开发者ID:luciang,项目名称:haiku,代码行数:101,代码来源:SpamFilter.cpp

示例13: _

status_t
StreamBase::Seek(uint32 flags, int64* frame, bigtime_t* time)
{
	BAutolock _(fStreamLock);

	if (fContext == NULL || fStream == NULL)
		return B_NO_INIT;

	TRACE_SEEK("StreamBase::Seek(%ld,%s%s%s%s, %lld, "
		"%lld)\n", VirtualIndex(),
		(flags & B_MEDIA_SEEK_TO_FRAME) ? " B_MEDIA_SEEK_TO_FRAME" : "",
		(flags & B_MEDIA_SEEK_TO_TIME) ? " B_MEDIA_SEEK_TO_TIME" : "",
		(flags & B_MEDIA_SEEK_CLOSEST_BACKWARD)
			? " B_MEDIA_SEEK_CLOSEST_BACKWARD" : "",
		(flags & B_MEDIA_SEEK_CLOSEST_FORWARD)
			? " B_MEDIA_SEEK_CLOSEST_FORWARD" : "",
		*frame, *time);

	double frameRate = FrameRate();
	if ((flags & B_MEDIA_SEEK_TO_FRAME) != 0) {
		// Seeking is always based on time, initialize it when client seeks
		// based on frame.
		*time = (bigtime_t)(*frame * 1000000.0 / frameRate + 0.5);
	}

	int64_t timeStamp = *time;

	int searchFlags = AVSEEK_FLAG_BACKWARD;
	if ((flags & B_MEDIA_SEEK_CLOSEST_FORWARD) != 0)
		searchFlags = 0;

	if (fSeekByBytes) {
		searchFlags |= AVSEEK_FLAG_BYTE;

		BAutolock _(fSourceLock);
		int64_t fileSize;
		if (fSource->GetSize(&fileSize) != B_OK)
			return B_NOT_SUPPORTED;
		int64_t duration = Duration();
		if (duration == 0)
			return B_NOT_SUPPORTED;

		timeStamp = int64_t(fileSize * ((double)timeStamp / duration));
		if ((flags & B_MEDIA_SEEK_CLOSEST_BACKWARD) != 0) {
			timeStamp -= 65536;
			if (timeStamp < 0)
				timeStamp = 0;
		}

		bool seekAgain = true;
		bool seekForward = true;
		bigtime_t lastFoundTime = -1;
		int64_t closestTimeStampBackwards = -1;
		while (seekAgain) {
			if (avformat_seek_file(fContext, -1, INT64_MIN, timeStamp,
				INT64_MAX, searchFlags) < 0) {
				TRACE("  avformat_seek_file() (by bytes) failed.\n");
				return B_ERROR;
			}
			seekAgain = false;

			// Our last packet is toast in any case. Read the next one so we
			// know where we really seeked.
			fReusePacket = false;
			if (_NextPacket(true) == B_OK) {
				while (fPacket.pts == kNoPTSValue) {
					fReusePacket = false;
					if (_NextPacket(true) != B_OK)
						return B_ERROR;
				}
				if (fPacket.pos >= 0)
					timeStamp = fPacket.pos;
				bigtime_t foundTime
					= _ConvertFromStreamTimeBase(fPacket.pts);
				if (foundTime != lastFoundTime) {
					lastFoundTime = foundTime;
					if (foundTime > *time) {
						if (closestTimeStampBackwards >= 0) {
							timeStamp = closestTimeStampBackwards;
							seekAgain = true;
							seekForward = false;
							continue;
						}
						int64_t diff = int64_t(fileSize
							* ((double)(foundTime - *time) / (2 * duration)));
						if (diff < 8192)
							break;
						timeStamp -= diff;
						TRACE_SEEK("  need to seek back (%lld) (time: %.2f "
							"-> %.2f)\n", timeStamp, *time / 1000000.0,
							foundTime / 1000000.0);
						if (timeStamp < 0)
							foundTime = 0;
						else {
							seekAgain = true;
							continue;
						}
					} else if (seekForward && foundTime < *time - 100000) {
						closestTimeStampBackwards = timeStamp;
						int64_t diff = int64_t(fileSize
//.........这里部分代码省略.........
开发者ID:RAZVOR,项目名称:haiku,代码行数:101,代码来源:AVFormatReader.cpp


注:本文中的BPositionIO类示例由纯净天空整理自Github/MSDocs等开源代码及文档管理平台,相关代码片段筛选自各路编程大神贡献的开源项目,源码版权归原作者所有,传播和使用请参考对应项目的License;未经允许,请勿转载。