1 /*-------------------------------------------------------------------------
2  * drawElements Quality Program Execution Server
3  * ---------------------------------------------
4  *
5  * Copyright 2014 The Android Open Source Project
6  *
7  * Licensed under the Apache License, Version 2.0 (the "License");
8  * you may not use this file except in compliance with the License.
9  * You may obtain a copy of the License at
10  *
11  *      http://www.apache.org/licenses/LICENSE-2.0
12  *
13  * Unless required by applicable law or agreed to in writing, software
14  * distributed under the License is distributed on an "AS IS" BASIS,
15  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
16  * See the License for the specific language governing permissions and
17  * limitations under the License.
18  *
19  *//*!
20  * \file
21  * \brief File Reader.
22  *//*--------------------------------------------------------------------*/
23 
24 #include "xsPosixFileReader.hpp"
25 
26 #include <vector>
27 
28 namespace xs
29 {
30 namespace posix
31 {
32 
FileReader(int blockSize,int numBlocks)33 FileReader::FileReader (int blockSize, int numBlocks)
34 	: m_file		(DE_NULL)
35 	, m_buf			(blockSize, numBlocks)
36 	, m_isRunning	(false)
37 {
38 }
39 
~FileReader(void)40 FileReader::~FileReader (void)
41 {
42 }
43 
start(const char * filename)44 void FileReader::start (const char* filename)
45 {
46 	DE_ASSERT(!m_isRunning);
47 
48 	m_file = deFile_create(filename, DE_FILEMODE_OPEN|DE_FILEMODE_READ);
49 	XS_CHECK(m_file);
50 
51 #if (DE_OS != DE_OS_IOS)
52 	// Set to non-blocking mode.
53 	if (!deFile_setFlags(m_file, DE_FILE_NONBLOCKING))
54 	{
55 		deFile_destroy(m_file);
56 		m_file = DE_NULL;
57 		XS_FAIL("Failed to set non-blocking mode");
58 	}
59 #endif
60 
61 	m_isRunning	= true;
62 
63 	de::Thread::start();
64 }
65 
run(void)66 void FileReader::run (void)
67 {
68 	std::vector<deUint8>	tmpBuf		(FILEREADER_TMP_BUFFER_SIZE);
69 	deInt64					numRead		= 0;
70 
71 	while (!m_buf.isCanceled())
72 	{
73 		deFileResult result = deFile_read(m_file, &tmpBuf[0], (deInt64)tmpBuf.size(), &numRead);
74 
75 		if (result == DE_FILERESULT_SUCCESS)
76 		{
77 			// Write to buffer.
78 			try
79 			{
80 				m_buf.write((int)numRead, &tmpBuf[0]);
81 				m_buf.flush();
82 			}
83 			catch (const ThreadedByteBuffer::CanceledException&)
84 			{
85 				// Canceled.
86 				break;
87 			}
88 		}
89 		else if (result == DE_FILERESULT_END_OF_FILE ||
90 				 result == DE_FILERESULT_WOULD_BLOCK)
91 		{
92 			// Wait for more data.
93 			deSleep(FILEREADER_IDLE_SLEEP);
94 		}
95 		else
96 			break; // Error.
97 	}
98 }
99 
stop(void)100 void FileReader::stop (void)
101 {
102 	if (!m_isRunning)
103 		return; // Nothing to do.
104 
105 	m_buf.cancel();
106 
107 	// Join thread.
108 	join();
109 
110 	// Destroy file.
111 	deFile_destroy(m_file);
112 	m_file = DE_NULL;
113 
114 	// Reset buffer.
115 	m_buf.clear();
116 
117 	m_isRunning = false;
118 }
119 
120 } // posix
121 } // xs
122