avi_generator.patch (4,749 bytes)
2008-02-14 00:13
Index: rts/Game/Game.cpp
===================================================================
--- rts/Game/Game.cpp (revision 5499)
+++ rts/Game/Game.cpp (working copy)
@@ -2358,7 +2358,11 @@
#ifndef NO_AVI
if(creatingVideo){
gu->lastFrameTime=1.0f/GAME_SPEED;
- aviGenerator->readOpenglPixelDataThreaded();
+ if(!aviGenerator->readOpenglPixelDataThreaded()){
+ creatingVideo = false;
+ delete aviGenerator;
+ aviGenerator = 0;
+ }
// logOutput.Print("Saved avi frame size %i %i",ih->biWidth,ih->biHeight);
}
#endif
Index: rts/System/Platform/Win/AVIGenerator.cpp
===================================================================
--- rts/System/Platform/Win/AVIGenerator.cpp (revision 5499)
+++ rts/System/Platform/Win/AVIGenerator.cpp (working copy)
@@ -123,14 +123,14 @@
AVIThread = 0;
}
- while(!freeDataPointers.empty()){
- unsigned char* tmp = freeDataPointers.front();
- freeDataPointers.pop_front();
+ while(!freeImageBuffers.empty()){
+ unsigned char* tmp = freeImageBuffers.front();
+ freeImageBuffers.pop_front();
delete [] tmp;
}
- while(!dataPointers.empty()){
- unsigned char* tmp = dataPointers.front();
- dataPointers.pop_front();
+ while(!imageBuffers.empty()){
+ unsigned char* tmp = imageBuffers.front();
+ imageBuffers.pop_front();
delete [] tmp;
}
@@ -146,8 +146,8 @@
assert(m_pAVIFile == NULL);
assert(m_pStream == NULL);
assert(m_pStreamCompressed == NULL);
- assert(freeDataPointers.empty());
- assert(dataPointers.empty());
+ assert(freeImageBuffers.empty());
+ assert(imageBuffers.empty());
assert(readBuf == NULL);
}
@@ -342,7 +342,7 @@
for(int i=0; i<10; i++){
unsigned char* tmpBuf = SAFE_NEW unsigned char[bitmapInfo.biSizeImage];
- freeDataPointers.push_back(tmpBuf);
+ freeImageBuffers.push_back(tmpBuf);
}
HWND mainWindow = FindWindow(NULL, ("Spring " + std::string(VERSION_STRING)).c_str());
@@ -378,28 +378,29 @@
}
-void CAVIGenerator::readOpenglPixelDataThreaded(){
+bool CAVIGenerator::readOpenglPixelDataThreaded(){
for(;;){
boost::mutex::scoped_lock lock(AVIMutex);
if(quitAVIgen){
- return;
+ return false;
}
if(readBuf != 0){
- dataPointers.push_back(readBuf);
+ imageBuffers.push_back(readBuf);
readBuf = 0;
AVICondition.notify_all();
}
- if(freeDataPointers.empty()){
+ if(freeImageBuffers.empty()){
AVICondition.wait(lock);
continue;
}
- readBuf = freeDataPointers.front();
- freeDataPointers.pop_front();
+ readBuf = freeImageBuffers.front();
+ freeImageBuffers.pop_front();
break;
}
glReadPixels(0, 0, bitmapInfo.biWidth, bitmapInfo.biHeight, GL_BGR_EXT, GL_UNSIGNED_BYTE, readBuf);
+ return true;
}
@@ -412,33 +413,41 @@
AVICondition.notify_all();
SetThreadPriority(GetCurrentThread(), THREAD_PRIORITY_BELOW_NORMAL);
unsigned char* localWriteBuf = 0;
+ bool encoderError = false;
for(;;){
{
boost::mutex::scoped_lock lock(AVIMutex);
+ if(encoderError){
+ logOutput.Print("The avi generator terminated unexpectedly!");
+ quitAVIgen = true;
+ //Do not let the main thread wait, as the encoder will not
+ //process and free the remaining content in imageBuffers.
+ AVICondition.notify_all();
+ }
if(quitAVIgen){
break;
}
if(localWriteBuf != 0){
- freeDataPointers.push_back(localWriteBuf);
+ freeImageBuffers.push_back(localWriteBuf);
localWriteBuf = 0;
AVICondition.notify_all();
}
- if(dataPointers.empty()){
+ if(imageBuffers.empty()){
AVICondition.wait(lock);
continue;
}
- localWriteBuf = dataPointers.front();
- dataPointers.pop_front();
+ localWriteBuf = imageBuffers.front();
+ imageBuffers.pop_front();
}
if(AddFrame(localWriteBuf)){
- quitAVIgen = true;
+ encoderError = true;
}
MSG msg;
//Handle all messages the codec sends.
while(PeekMessage(&msg, NULL, 0, 0, PM_NOREMOVE)){
if(GetMessage(&msg, NULL, 0, 0) < 0){
- quitAVIgen = true;
+ encoderError = true;
break;
}
TranslateMessage(&msg);
Index: rts/System/Platform/Win/AVIGenerator.h
===================================================================
--- rts/System/Platform/Win/AVIGenerator.h (revision 5499)
+++ rts/System/Platform/Win/AVIGenerator.h (working copy)
@@ -25,7 +25,7 @@
//Returns last error message
std::string GetLastErrorMessage() const {return errorMsg;}
- void readOpenglPixelDataThreaded();
+ bool readOpenglPixelDataThreaded();
private:
@@ -48,8 +48,8 @@
boost::condition AVICondition;
- std::list<unsigned char*> freeDataPointers;
- std::list<unsigned char*> dataPointers;
+ std::list<unsigned char*> freeImageBuffers;
+ std::list<unsigned char*> imageBuffers;
unsigned char* readBuf;