Fixes Issue 419 by checking validity of StdHandle values. Also:

* handful of minor code cleanups, and some warning removals for ICC.
 * replaced the dualshock.png with a dualshock.jpg (120k smaller!)
 * Updated the About Box, and added Zeydlitz / ZZogl to the plugin author credits.

git-svn-id: http://pcsx2.googlecode.com/svn/trunk@1902 96395faa-99c1-11dd-bbfe-3dabce05a288
This commit is contained in:
Jake.Stine 2009-09-22 04:37:11 +00:00
parent 1c7719e0ec
commit 6907b78640
19 changed files with 155 additions and 159 deletions

View File

@ -70,7 +70,11 @@
# endif # endif
# else # else
# define jBREAKPOINT() __debugbreak(); # define jBREAKPOINT() __debugbreak();
# define jASSUME(exp) do { if(exp) ; else jBREAKPOINT(); } while(0); # ifdef wxASSERT
# define jASSUME(exp) wxASSERT(exp)
# else
# define jASSUME(exp) do { if(exp) ; else jBREAKPOINT(); } while(0);
# endif
# endif # endif
#endif #endif

View File

@ -203,7 +203,7 @@ namespace x86Emitter
Factor++; Factor++;
else else
{ {
jASSUME( Index.IsEmpty() ); // or die if we already have an index! DevAssert( Index.IsEmpty(), "x86Emitter: Only one scaled index register is allowed in an address modifier." );
Index = src; Index = src;
Factor = 2; Factor = 2;
} }
@ -213,7 +213,7 @@ namespace x86Emitter
else if( Index.IsEmpty() ) else if( Index.IsEmpty() )
Index = src; Index = src;
else else
assert( false ); // oops, only 2 regs allowed per ModRm! wxASSERT_MSG( false, L"x86Emitter: address modifiers cannot have more than two index registers." ); // oops, only 2 regs allowed per ModRm!
return *this; return *this;
} }
@ -237,7 +237,7 @@ namespace x86Emitter
else if( Index == src.Index ) else if( Index == src.Index )
Factor++; Factor++;
else else
assert( false ); // oops, only 2 regs allowed! wxASSERT_MSG( false, L"x86Emitter: address modifiers cannot have more than two index registers." ); // oops, only 2 regs allowed per ModRm!
return *this; return *this;
} }
@ -283,7 +283,7 @@ namespace x86Emitter
{ {
if( !is_s8( displacement ) ) if( !is_s8( displacement ) )
{ {
assert( false ); wxASSERT( false );
// Don't ask. --arcum42 // Don't ask. --arcum42
#if !defined(__LINUX__) || !defined(DEBUG) #if !defined(__LINUX__) || !defined(DEBUG)

View File

@ -282,7 +282,7 @@ int TranslateGDKtoWXK( u32 keysym )
// window, same as the Win32 one. Not sure how doable it is, and it's not as urgent // window, same as the Win32 one. Not sure how doable it is, and it's not as urgent
// anyway since Linux has better generic console support and commandline piping. // anyway since Linux has better generic console support and commandline piping.
// //
PipeRedirectionBase* NewPipeRedir() PipeRedirectionBase* NewPipeRedir( FILE* stdstream )
{ {
return NULL; return NULL;
} }

View File

@ -664,8 +664,7 @@ PluginManager::PluginManager( const wxString (&folders)[PluginId_Count] )
{ {
Console::Status( "Loading plugins..." ); Console::Status( "Loading plugins..." );
const PluginInfo* pi = tbl_PluginInfo-1; const PluginInfo* pi = tbl_PluginInfo; do
while( ++pi, pi->shortname != NULL )
{ {
const PluginsEnum_t pid = pi->id; const PluginsEnum_t pid = pi->id;
@ -700,7 +699,7 @@ PluginManager::PluginManager( const wxString (&folders)[PluginId_Count] )
// Bind Optional Functions // Bind Optional Functions
// (leave pointer null and do not generate error) // (leave pointer null and do not generate error)
} } while( ++pi, pi->shortname != NULL );
// Hack for PAD's stupid parameter passed on Init // Hack for PAD's stupid parameter passed on Init
PADinit = (_PADinit)m_info[PluginId_PAD].CommonBindings.Init; PADinit = (_PADinit)m_info[PluginId_PAD].CommonBindings.Init;
@ -916,9 +915,9 @@ void PluginManager::Open()
{ {
Console::Status( "Opening plugins..." ); Console::Status( "Opening plugins..." );
const PluginInfo* pi = tbl_PluginInfo-1; const PluginInfo* pi = tbl_PluginInfo; do {
while( ++pi, pi->shortname != NULL )
g_plugins->Open( pi->id ); g_plugins->Open( pi->id );
} while( ++pi, pi->shortname != NULL );
Console::Status( "Plugins opened successfully." ); Console::Status( "Plugins opened successfully." );
} }
@ -970,8 +969,7 @@ void PluginManager::Close( bool closegs )
void PluginManager::Init() void PluginManager::Init()
{ {
bool printlog = false; bool printlog = false;
const PluginInfo* pi = tbl_PluginInfo-1; const PluginInfo* pi = tbl_PluginInfo; do
while( ++pi, pi->shortname != NULL )
{ {
const PluginsEnum_t pid = pi->id; const PluginsEnum_t pid = pi->id;
@ -985,7 +983,7 @@ void PluginManager::Init()
m_info[pid].IsInitialized = true; m_info[pid].IsInitialized = true;
if( 0 != m_info[pid].CommonBindings.Init() ) if( 0 != m_info[pid].CommonBindings.Init() )
throw Exception::PluginInitError( pid ); throw Exception::PluginInitError( pid );
} } while( ++pi, pi->shortname != NULL );
if( EmuPlugins.Mcd == NULL ) if( EmuPlugins.Mcd == NULL )
{ {
@ -1106,13 +1104,10 @@ void PluginManager::Freeze( PluginsEnum_t pid, SaveStateBase& state )
bool PluginManager::KeyEvent( const keyEvent& evt ) bool PluginManager::KeyEvent( const keyEvent& evt )
{ {
const PluginInfo* pi = tbl_PluginInfo-1; const PluginInfo* pi = tbl_PluginInfo; do {
while( ++pi, pi->shortname != NULL )
{
if( pi->id != PluginId_PAD ) if( pi->id != PluginId_PAD )
m_info[pi->id].CommonBindings.KeyEvent( const_cast<keyEvent*>(&evt) ); m_info[pi->id].CommonBindings.KeyEvent( const_cast<keyEvent*>(&evt) );
} } while( ++pi, pi->shortname != NULL );
return false; return false;
} }
@ -1135,9 +1130,9 @@ PluginManager* PluginManager_Create( const wxChar* (&folders)[PluginId_Count] )
{ {
wxString passins[PluginId_Count]; wxString passins[PluginId_Count];
const PluginInfo* pi = tbl_PluginInfo-1; const PluginInfo* pi = tbl_PluginInfo; do {
while( ++pi, pi->shortname != NULL )
passins[pi->id] = folders[pi->id]; passins[pi->id] = folders[pi->id];
} while( ++pi, pi->shortname != NULL );
return PluginManager_Create( passins ); return PluginManager_Create( passins );
} }

View File

@ -318,22 +318,20 @@ __forceinline void _vuAddLowerStalls(VURegs * VU, _VURegsNum *VUregsn) {
#ifndef INT_VUDOUBLEHACK #ifndef INT_VUDOUBLEHACK
static float __fastcall vuDouble(u32 f) static float __fastcall vuDouble(u32 f)
{ {
switch(f & 0x7f800000){ switch(f & 0x7f800000)
{
case 0x0: case 0x0:
f &= 0x80000000; f &= 0x80000000;
return *(float*)&f; return *(float*)&f;
break; break;
case 0x7f800000: case 0x7f800000:
{ {
u32 d; u32 d = (f & 0x80000000)|0x7f7fffff;
d = (f & 0x80000000)|0x7f7fffff;
return *(float*)&d; return *(float*)&d;
break; break;
} }
default:
return *(float*)&f;
break;
} }
return *(float*)&f;
} }
#else #else
static __forceinline float vuDouble(u32 f) static __forceinline float vuDouble(u32 f)

View File

@ -298,7 +298,8 @@ protected:
wxScopedPtr<wxImageList> m_ToolbarImages; wxScopedPtr<wxImageList> m_ToolbarImages;
wxScopedPtr<wxBitmap> m_Bitmap_Logo; wxScopedPtr<wxBitmap> m_Bitmap_Logo;
wxScopedPtr<PipeRedirectionBase>m_PipeRedirHandle; wxScopedPtr<PipeRedirectionBase>m_StdoutRedirHandle;
wxScopedPtr<PipeRedirectionBase>m_StderrRedirHandle;
public: public:
wxScopedPtr<SysCoreAllocations> m_CoreAllocs; wxScopedPtr<SysCoreAllocations> m_CoreAllocs;

View File

@ -325,13 +325,11 @@ void Pcsx2App::OnInitCmdLine( wxCmdLineParser& parser )
parser.AddSwitch( wxEmptyString,L"forcewiz",_("Forces PCSX2 to start the First-time Wizard") ); parser.AddSwitch( wxEmptyString,L"forcewiz",_("Forces PCSX2 to start the First-time Wizard") );
const PluginInfo* pi = tbl_PluginInfo-1; const PluginInfo* pi = tbl_PluginInfo; do {
while( ++pi, pi->shortname != NULL )
{
parser.AddOption( wxEmptyString, pi->GetShortname().Lower(), parser.AddOption( wxEmptyString, pi->GetShortname().Lower(),
wxsFormat( _("specify the file to use as the %s plugin"), pi->GetShortname().c_str() ) wxsFormat( _("specify the file to use as the %s plugin"), pi->GetShortname().c_str() )
); );
} } while( ++pi, pi->shortname != NULL );
parser.SetSwitchChars( L"-" ); parser.SetSwitchChars( L"-" );
} }
@ -356,8 +354,7 @@ bool Pcsx2App::OnCmdLineParsed( wxCmdLineParser& parser )
//bool yay = parser.Found(L"nogui"); //bool yay = parser.Found(L"nogui");
m_ForceWizard = parser.Found( L"forcewiz" ); m_ForceWizard = parser.Found( L"forcewiz" );
const PluginInfo* pi = tbl_PluginInfo-1; const PluginInfo* pi = tbl_PluginInfo; do
while( ++pi, pi->shortname != NULL )
{ {
wxString dest; wxString dest;
if( !parser.Found( pi->GetShortname().Lower(), &dest ) ) continue; if( !parser.Found( pi->GetShortname().Lower(), &dest ) ) continue;
@ -377,7 +374,7 @@ bool Pcsx2App::OnCmdLineParsed( wxCmdLineParser& parser )
if( !result ) return false; if( !result ) return false;
} }
} } while( ++pi, pi->shortname != NULL );
parser.Found( L"cfgpath", &OverrideOptions.SettingsFolder ); parser.Found( L"cfgpath", &OverrideOptions.SettingsFolder );
@ -394,16 +391,9 @@ bool Pcsx2App::OnInit()
g_Conf.reset( new AppConfig() ); g_Conf.reset( new AppConfig() );
try m_StdoutRedirHandle.reset( NewPipeRedir(stdout) );
{ m_StderrRedirHandle.reset( NewPipeRedir(stderr) );
m_PipeRedirHandle.reset( NewPipeRedir() ); wxLocale::AddCatalogLookupPathPrefix( wxGetCwd() );
wxLocale::AddCatalogLookupPathPrefix( wxGetCwd() );
}
catch( Exception::RuntimeError& ex )
{
// Entirely non-critical errors. Log 'em and move along.
Console::Error( ex.FormatDiagnosticMessage() );
}
#define pxMessageBoxEventThing(func) \ #define pxMessageBoxEventThing(func) \
(wxObjectEventFunction)(wxEventFunction)wxStaticCastEvent(pxMessageBoxEventFunction, &func ) (wxObjectEventFunction)(wxEventFunction)wxStaticCastEvent(pxMessageBoxEventFunction, &func )

View File

@ -42,7 +42,7 @@ protected:
PipeRedirectionBase() {} PipeRedirectionBase() {}
}; };
extern PipeRedirectionBase* NewPipeRedir(); extern PipeRedirectionBase* NewPipeRedir( FILE* stdstream );
// -------------------------------------------------------------------------------------- // --------------------------------------------------------------------------------------
// pxLogConsole // pxLogConsole

View File

@ -47,19 +47,18 @@ namespace Dialogs
// -------------------------------------------------------------------------------------- // --------------------------------------------------------------------------------------
Dialogs::AboutBoxDialog::AboutBoxDialog( wxWindow* parent, int id ): Dialogs::AboutBoxDialog::AboutBoxDialog( wxWindow* parent, int id ):
wxDialog( parent, id, _("About PCSX2"), parent->GetPosition()-wxSize( 32, 32 ) ), wxDialogWithHelpers( parent, id, _("About PCSX2"), false ),
m_bitmap_logo( this, wxID_ANY, wxGetApp().GetLogoBitmap(), m_bitmap_dualshock( this, wxID_ANY, wxBitmap( EmbeddedImage<res_Dualshock>().Get() ),
wxDefaultPosition, wxDefaultSize, wxBORDER_SUNKEN ),
m_bitmap_ps2system( this, wxID_ANY, wxBitmap( EmbeddedImage<res_Dualshock>().Get() ),
wxDefaultPosition, wxDefaultSize, wxBORDER_SUNKEN ) wxDefaultPosition, wxDefaultSize, wxBORDER_SUNKEN )
{ {
static const wxString LabelAuthors = wxString::FromAscii( static const wxString LabelAuthors = wxString::FromUTF8(
"PCSX2, a PS2 emulator\n\n" "Developers"
"Active Devs: Arcum42, Refraction,"
"drk||raziel, cottonvibes, gigaherz,"
"rama, Jake.Stine, saqib, Tmkk"
"\n\n" "\n\n"
"Inactive devs: Alexey silinov, Aumatt," "v0.9.6+: Arcum42, Refraction,"
"drk||raziel, cottonvibes, gigaherz,"
"rama, Jake.Stine, saqib, Tmkk, pseudonym"
"\n\n"
"Previous versions: Alexey silinov, Aumatt,"
"Florin, goldfinger, Linuzappz, loser," "Florin, goldfinger, Linuzappz, loser,"
"Nachbrenner, shadow, Zerofrog" "Nachbrenner, shadow, Zerofrog"
"\n\n" "\n\n"
@ -70,19 +69,23 @@ Dialogs::AboutBoxDialog::AboutBoxDialog( wxWindow* parent, int id ):
"Webmasters: CKemu, Falcon4ever" "Webmasters: CKemu, Falcon4ever"
); );
static const wxString LabelGreets = wxString::FromAscii( static const wxString LabelGreets = wxString::FromUTF8(
"Contributors: Hiryu and Sjeep for libcvd (the iso parsing and\n" "Contributors"
"filesystem driver code), nneeve, pseudonym\n" "\n\n"
"\n" "Hiryu and Sjeep for libcvd (the iso parsing and"
"Plugin Specialists: ChickenLiver (Lilypad), Efp (efp),\n" "filesystem driver code), nneeve (fpu and vu help)"
"Gabest (Gsdx, Cdvdolio, Xpad)\n" "\n\n"
"\n" "Plugin Specialists: ChickenLiver (Lilypad), Efp (efp),"
"Special thanks to: black_wd, Belmont, BGome, _Demo_, Dreamtime,\n" "Gabest (Gsdx, Cdvdolio, Xpad), Zeydlitz (ZZogl)"
"\n\n"
"Special thanks to: black_wd, Belmont, BGome, _Demo_, Dreamtime,"
"F|RES, MrBrown, razorblade, Seta-san, Skarmeth" "F|RES, MrBrown, razorblade, Seta-san, Skarmeth"
); );
wxBoxSizer& mainSizer = *new wxBoxSizer( wxVERTICAL ); wxBoxSizer& mainSizer = *new wxBoxSizer( wxVERTICAL );
AddStaticText( mainSizer, _("PCSX2 - Playstation 2 Emulator") );
// This sizer holds text of the authors and a logo! // This sizer holds text of the authors and a logo!
wxBoxSizer& AuthLogoSizer = *new wxBoxSizer( wxHORIZONTAL ); wxBoxSizer& AuthLogoSizer = *new wxBoxSizer( wxHORIZONTAL );
@ -95,20 +98,19 @@ Dialogs::AboutBoxDialog::AboutBoxDialog( wxWindow* parent, int id ):
StaticTextCentered* label_auth = new StaticTextCentered( this, LabelAuthors ); StaticTextCentered* label_auth = new StaticTextCentered( this, LabelAuthors );
StaticTextCentered* label_greets = new StaticTextCentered( this, LabelGreets ); StaticTextCentered* label_greets = new StaticTextCentered( this, LabelGreets );
label_auth->Wrap( m_bitmap_logo.GetSize().GetWidth() / 2 ); label_auth->Wrap( 340 );
label_greets->Wrap( (m_bitmap_logo.GetSize().GetWidth() * 4) / 3 ); label_greets->Wrap( 200 );
aboutUs.Add( label_auth, SizerFlags::StdSpace() ); aboutUs.Add( label_auth, SizerFlags::StdExpand() );
contribs.Add( label_greets, SizerFlags::StdExpand() ); contribs.Add( label_greets, SizerFlags::StdExpand() );
AuthLogoSizer.Add( &aboutUs ); AuthLogoSizer.Add( &aboutUs );
AuthLogoSizer.AddSpacer( 7 ); AuthLogoSizer.AddSpacer( 7 );
AuthLogoSizer.Add( &m_bitmap_logo, wxSizerFlags().Border( wxALL, 4 ) ); AuthLogoSizer.Add( &contribs );
ContribSizer.AddStretchSpacer( 1 ); ContribSizer.AddStretchSpacer( 1 );
ContribSizer.Add( &m_bitmap_ps2system, SizerFlags::StdSpace() ); ContribSizer.Add( &m_bitmap_dualshock, SizerFlags::StdSpace() );
ContribSizer.AddStretchSpacer( 1 ); ContribSizer.AddStretchSpacer( 1 );
ContribSizer.Add( &contribs, wxSizerFlags(7).HorzBorder().Expand() );
mainSizer.Add( &AuthLogoSizer, SizerFlags::StdSpace() ); mainSizer.Add( &AuthLogoSizer, SizerFlags::StdSpace() );
@ -123,4 +125,6 @@ Dialogs::AboutBoxDialog::AboutBoxDialog( wxWindow* parent, int id ):
mainSizer.Add( new wxButton( this, wxID_OK, L"I've seen enough"), SizerFlags::StdCenter() ); mainSizer.Add( new wxButton( this, wxID_OK, L"I've seen enough"), SizerFlags::StdCenter() );
SetSizerAndFit( &mainSizer ); SetSizerAndFit( &mainSizer );
CenterOnScreen();
} }

View File

@ -121,7 +121,7 @@ FirstTimeWizard::FirstTimeWizard( wxWindow* parent ) :
Connect( wxEVT_COMMAND_LISTBOX_DOUBLECLICKED, wxCommandEventHandler(FirstTimeWizard::OnDoubleClicked) ); Connect( wxEVT_COMMAND_LISTBOX_DOUBLECLICKED, wxCommandEventHandler(FirstTimeWizard::OnDoubleClicked) );
} }
FirstTimeWizard::~FirstTimeWizard() FirstTimeWizard::~FirstTimeWizard() throw()
{ {
g_ApplyState.DoCleanup(); g_ApplyState.DoCleanup();
} }

View File

@ -48,7 +48,7 @@ protected:
public: public:
FirstTimeWizard( wxWindow* parent ); FirstTimeWizard( wxWindow* parent );
virtual ~FirstTimeWizard(); virtual ~FirstTimeWizard() throw();
wxWizardPage *GetUsermodePage() const { return &m_page_usermode; } wxWizardPage *GetUsermodePage() const { return &m_page_usermode; }
wxWizardPage *GetPostUsermodePage() const { return &m_page_plugins; } wxWizardPage *GetPostUsermodePage() const { return &m_page_plugins; }
@ -66,15 +66,15 @@ protected:
namespace Dialogs namespace Dialogs
{ {
class AboutBoxDialog: public wxDialog class AboutBoxDialog: public wxDialogWithHelpers
{ {
public: public:
AboutBoxDialog( wxWindow* parent=NULL, int id=DialogId_About ); AboutBoxDialog( wxWindow* parent=NULL, int id=DialogId_About );
virtual ~AboutBoxDialog() throw() {}
protected: protected:
wxStaticBitmap m_bitmap_logo; //wxStaticBitmap m_bitmap_logo;
wxStaticBitmap m_bitmap_ps2system; wxStaticBitmap m_bitmap_dualshock;
}; };
class PickUserModeDialog : public wxDialogWithHelpers class PickUserModeDialog : public wxDialogWithHelpers
@ -85,6 +85,7 @@ namespace Dialogs
public: public:
PickUserModeDialog( wxWindow* parent, int id=wxID_ANY ); PickUserModeDialog( wxWindow* parent, int id=wxID_ANY );
virtual ~PickUserModeDialog() throw() {}
protected: protected:
void OnOk_Click( wxCommandEvent& evt ); void OnOk_Click( wxCommandEvent& evt );
@ -95,6 +96,7 @@ namespace Dialogs
{ {
public: public:
ImportSettingsDialog( wxWindow* parent ); ImportSettingsDialog( wxWindow* parent );
virtual ~ImportSettingsDialog() throw() {}
protected: protected:
void OnImport_Click( wxCommandEvent& evt ); void OnImport_Click( wxCommandEvent& evt );

View File

@ -114,7 +114,7 @@ namespace Panels
void StartWizard(); void StartWizard();
bool ApplyAll( bool saveOnSuccess=true ); bool ApplyAll( bool saveOnSuccess=true );
bool ApplyPage( int pageid, bool saveOnSuccess=true ); bool ApplyPage( int pageid, bool saveOnSuccess=true );
void DoCleanup(); void DoCleanup() throw();
}; };
extern StaticApplyState g_ApplyState; extern StaticApplyState g_ApplyState;

View File

@ -30,7 +30,7 @@ Panels::StaticApplyState Panels::g_ApplyState;
// on dialog destruction. It asserts if the ApplyList hasn't been cleaned up // on dialog destruction. It asserts if the ApplyList hasn't been cleaned up
// and then cleans it up forcefully. // and then cleans it up forcefully.
// //
void Panels::StaticApplyState::DoCleanup() void Panels::StaticApplyState::DoCleanup() throw()
{ {
wxASSERT_MSG( PanelList.size() != 0, L"PanelList list hasn't been cleaned up." ); wxASSERT_MSG( PanelList.size() != 0, L"PanelList list hasn't been cleaned up." );
PanelList.clear(); PanelList.clear();

View File

@ -303,12 +303,10 @@ void Panels::PluginSelectorPanel::Apply()
// Need to unload the current emulation state if the user changed plugins, because // Need to unload the current emulation state if the user changed plugins, because
// the whole plugin system needs to be re-loaded. // the whole plugin system needs to be re-loaded.
const PluginInfo* pi = tbl_PluginInfo-1; const PluginInfo* pi = tbl_PluginInfo; do {
while( ++pi, pi->shortname != NULL )
{
if( g_Conf->FullpathTo( pi->id ) != g_Conf->FullpathTo( pi->id ) ) if( g_Conf->FullpathTo( pi->id ) != g_Conf->FullpathTo( pi->id ) )
break; break;
} } while( ++pi, pi->shortname != NULL );
if( pi->shortname != NULL ) if( pi->shortname != NULL )
{ {

View File

@ -158,14 +158,13 @@ void Pcsx2App::ReloadPlugins()
wxString passins[PluginId_Count]; wxString passins[PluginId_Count];
const PluginInfo* pi = tbl_PluginInfo-1; const PluginInfo* pi = tbl_PluginInfo; do
while( ++pi, pi->shortname != NULL )
{ {
passins[pi->id] = OverrideOptions.Filenames[pi->id].GetFullPath(); passins[pi->id] = OverrideOptions.Filenames[pi->id].GetFullPath();
if( passins[pi->id].IsEmpty() || !wxFileExists( passins[pi->id] ) ) if( passins[pi->id].IsEmpty() || !wxFileExists( passins[pi->id] ) )
passins[pi->id] = g_Conf->FullpathTo( pi->id ); passins[pi->id] = g_Conf->FullpathTo( pi->id );
} } while( ++pi, pi->shortname != NULL );
_loadTask.reset( new LoadPluginsTask( passins ) ); _loadTask.reset( new LoadPluginsTask( passins ) );
// ... and when it finishes it posts up a OnLoadPluginsComplete(). Bye. :) // ... and when it finishes it posts up a OnLoadPluginsComplete(). Bye. :)

Binary file not shown.

After

Width:  |  Height:  |  Size: 24 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 152 KiB

View File

@ -2362,7 +2362,7 @@
</FileConfiguration> </FileConfiguration>
</File> </File>
<File <File
RelativePath="..\..\gui\Resources\Dualshock.png" RelativePath="..\..\gui\Resources\Dualshock.jpg"
> >
<FileConfiguration <FileConfiguration
Name="Debug|Win32" Name="Debug|Win32"
@ -2370,7 +2370,7 @@
<Tool <Tool
Name="VCCustomBuildTool" Name="VCCustomBuildTool"
Description="" Description=""
CommandLine="&quot;$(InputDir)\bin2cpp.cmd&quot; $(InputFileName)&#x0D;&#x0A;" CommandLine="&quot;$(InputDir)\bin2cpp.cmd&quot; $(InputFileName)"
Outputs="&quot;$(InputDir)\$(InputName).h" Outputs="&quot;$(InputDir)\$(InputName).h"
/> />
</FileConfiguration> </FileConfiguration>
@ -2380,7 +2380,7 @@
<Tool <Tool
Name="VCCustomBuildTool" Name="VCCustomBuildTool"
Description="" Description=""
CommandLine="&quot;$(InputDir)\bin2cpp.cmd&quot; $(InputFileName)&#x0D;&#x0A;" CommandLine="&quot;$(InputDir)\bin2cpp.cmd&quot; $(InputFileName)"
Outputs="&quot;$(InputDir)\$(InputName).h" Outputs="&quot;$(InputDir)\$(InputName).h"
/> />
</FileConfiguration> </FileConfiguration>
@ -2390,7 +2390,7 @@
<Tool <Tool
Name="VCCustomBuildTool" Name="VCCustomBuildTool"
Description="" Description=""
CommandLine="&quot;$(InputDir)\bin2cpp.cmd&quot; $(InputFileName)&#x0D;&#x0A;" CommandLine="&quot;$(InputDir)\bin2cpp.cmd&quot; $(InputFileName)"
Outputs="&quot;$(InputDir)\$(InputName).h" Outputs="&quot;$(InputDir)\$(InputName).h"
/> />
</FileConfiguration> </FileConfiguration>

View File

@ -72,14 +72,14 @@ namespace Exception
using namespace Threading; using namespace Threading;
static void CreatePipe( HANDLE& ph_Pipe, HANDLE& ph_File ) static __forceinline void CreatePipe( HANDLE& ph_Pipe, HANDLE& ph_File )
{ {
// Create a threadsafe unique name for the Pipe // Create a threadsafe unique name for the Pipe
static int s32_Counter = 0; static int s32_Counter = 0;
wxString s_PipeName; wxString s_PipeName;
s_PipeName.Printf( L"\\\\.\\pipe\\pcsxPipe%X_%X_%X_%X", s_PipeName.Printf( L"\\\\.\\pipe\\pcsxPipe%X_%X_%X_%X",
GetCurrentProcessId(), GetCurrentThreadId(), GetTickCount(), s32_Counter++); GetCurrentProcessId(), GetCurrentThreadId(), GetTickCount(), ++s32_Counter);
SECURITY_ATTRIBUTES k_Secur; SECURITY_ATTRIBUTES k_Secur;
k_Secur.nLength = sizeof(SECURITY_ATTRIBUTES); k_Secur.nLength = sizeof(SECURITY_ATTRIBUTES);
@ -108,8 +108,10 @@ static void CreatePipe( HANDLE& ph_Pipe, HANDLE& ph_File )
// Reads from the Pipe and appends the read data to ps_Data // Reads from the Pipe and appends the read data to ps_Data
// returns TRUE if something was printed to console, or false if the stdout/err were idle. // returns TRUE if something was printed to console, or false if the stdout/err were idle.
static bool ReadPipe(HANDLE h_Pipe, Console::Colors color ) static __forceinline bool ReadPipe(HANDLE h_Pipe, Console::Colors color )
{ {
if( h_Pipe == INVALID_HANDLE_VALUE ) return false;
// IMPORTANT: Check if there is data that can be read. // IMPORTANT: Check if there is data that can be read.
// The first console output will be lost if ReadFile() is called before data becomes available! // The first console output will be lost if ReadFile() is called before data becomes available!
// It does not make any sense but the following 5 lines are indispensable!! // It does not make any sense but the following 5 lines are indispensable!!
@ -143,22 +145,19 @@ static bool ReadPipe(HANDLE h_Pipe, Console::Colors color )
class WinPipeThread : public PersistentThread class WinPipeThread : public PersistentThread
{ {
protected: protected:
const HANDLE& mh_OutPipe; const HANDLE& m_outpipe;
const HANDLE& mh_ErrPipe; const Console::Colors m_color;
public: public:
WinPipeThread( const HANDLE& outpipe, const HANDLE& errpipe ) : WinPipeThread( const HANDLE& outpipe, Console::Colors color ) :
mh_OutPipe( outpipe ) m_outpipe( outpipe )
, mh_ErrPipe( errpipe ) , m_color( color )
//, mk_OverOut( overout )
//, mk_OverErr( overerr )
{ {
} }
virtual ~WinPipeThread() throw() virtual ~WinPipeThread() throw()
{ {
PersistentThread::Cancel(); PersistentThread::Cancel();
SetThreadPriority( GetCurrentThread(), THREAD_PRIORITY_BELOW_NORMAL );
} }
protected: protected:
@ -166,12 +165,12 @@ protected:
{ {
try try
{ {
SetThreadPriority( GetCurrentThread(), THREAD_PRIORITY_BELOW_NORMAL );
while( true ) while( true )
{ {
Sleep( 100 ); Sleep( 100 );
pthread_testcancel(); pthread_testcancel();
ReadPipe(mh_OutPipe, Color_Black ); ReadPipe(m_outpipe, m_color );
ReadPipe(mh_ErrPipe, Color_Red );
} }
} }
catch( Exception::Win32Error& ex ) catch( Exception::Win32Error& ex )
@ -189,88 +188,94 @@ class WinPipeRedirection : public PipeRedirectionBase
DeclareNoncopyableObject( WinPipeRedirection ); DeclareNoncopyableObject( WinPipeRedirection );
protected: protected:
HANDLE mh_OutPipe; HANDLE m_pipe;
HANDLE mh_ErrPipe; HANDLE m_file;
HANDLE mh_OutFile; int m_crtFile;
HANDLE mh_ErrFile; FILE* m_fp;
int m_hCrtOut;
int m_hCrtErr;
FILE* h_fpOut;
FILE* h_fpErr;
WinPipeThread m_Thread; WinPipeThread m_Thread;
public: public:
WinPipeRedirection(); WinPipeRedirection( FILE* stdstream );
virtual ~WinPipeRedirection() throw(); virtual ~WinPipeRedirection() throw();
void Cleanup() throw();
}; };
WinPipeRedirection::WinPipeRedirection() : WinPipeRedirection::WinPipeRedirection( FILE* stdstream ) :
mh_OutPipe(INVALID_HANDLE_VALUE) m_pipe(INVALID_HANDLE_VALUE)
, mh_ErrPipe(INVALID_HANDLE_VALUE) , m_file(INVALID_HANDLE_VALUE)
, mh_OutFile(INVALID_HANDLE_VALUE) , m_crtFile(-1)
, mh_ErrFile(INVALID_HANDLE_VALUE) , m_fp(NULL)
, m_hCrtOut(-1) , m_Thread( m_pipe, (stdstream == stderr) ? Color_Red : Color_Black )
, m_hCrtErr(-1)
, h_fpOut(NULL)
, h_fpErr(NULL)
, m_Thread( mh_OutPipe, mh_ErrPipe )
{ {
CreatePipe(mh_OutPipe, mh_OutFile ); try
CreatePipe(mh_ErrPipe, mh_ErrFile ); {
wxASSERT( stdstream == stderr || stdstream == stdout );
DWORD stdhandle = ( stdstream == stderr ) ? STD_ERROR_HANDLE : STD_OUTPUT_HANDLE;
SetStdHandle( STD_OUTPUT_HANDLE, mh_OutFile ); CreatePipe( m_pipe, m_file );
SetStdHandle( STD_ERROR_HANDLE, mh_ErrFile ); SetStdHandle( stdhandle, m_file );
m_hCrtOut = _open_osfhandle( (intptr_t)GetStdHandle(STD_OUTPUT_HANDLE), _O_TEXT ); // In some cases GetStdHandle can fail, even when the one we just assigned above is valid.
m_hCrtErr = _open_osfhandle( (intptr_t)GetStdHandle(STD_ERROR_HANDLE), _O_TEXT ); HANDLE newhandle = GetStdHandle(stdhandle);
if( newhandle == INVALID_HANDLE_VALUE )
throw Exception::Win32Error( "GetStdHandle failed." );
h_fpOut = _fdopen( m_hCrtOut, "w" ); if( newhandle == NULL )
h_fpErr = _fdopen( m_hCrtErr, "w" ); throw Exception::RuntimeError( "GetStdHandle returned NULL." ); // not a Win32error (no error code)
*stdout = *h_fpOut; m_crtFile = _open_osfhandle( (intptr_t)newhandle, _O_TEXT );
*stderr = *h_fpErr; m_fp = _fdopen( m_crtFile, "w" );
setvbuf( stdout, NULL, _IONBF, 0 ); *stdstream = *m_fp;
setvbuf( stderr, NULL, _IONBF, 0 ); setvbuf( stdstream, NULL, _IONBF, 0 );
m_Thread.Start(); m_Thread.Start();
}
catch( ... )
{
Cleanup(); throw;
}
} }
WinPipeRedirection::~WinPipeRedirection() throw() WinPipeRedirection::~WinPipeRedirection()
{
Cleanup();
}
void WinPipeRedirection::Cleanup() throw()
{ {
m_Thread.Cancel(); m_Thread.Cancel();
#define safe_CloseHandle( ptr ) \ if( m_fp != NULL )
((void) (( ( ptr != INVALID_HANDLE_VALUE ) && (!!CloseHandle( ptr ), !!0) ), ptr = INVALID_HANDLE_VALUE))
safe_CloseHandle(mh_OutPipe);
safe_CloseHandle(mh_ErrPipe);
if( h_fpOut != NULL )
{ {
fclose( h_fpOut ); fclose( m_fp );
h_fpOut = NULL; m_fp = NULL;
}
if( h_fpErr != NULL )
{
fclose( h_fpErr );
h_fpErr = NULL;
} }
#define safe_close( ptr ) \ // crtFile is closed implicitly when closing m_fp
((void) (( ( ptr != -1 ) && (!!_close( ptr ), !!0) ), ptr = -1)) // m_file is closed implicitly when closing crtFile
// CrtOut and CrtErr are closed implicitly when closing fpOut/fpErr if( m_pipe != INVALID_HANDLE_VALUE )
// OutFile and ErrFile are closed implicitly when closing m_hCrtOut/Err {
CloseHandle( m_pipe );
m_pipe = INVALID_HANDLE_VALUE;
}
} }
// The win32 specific implementation of PipeRedirection. // The win32 specific implementation of PipeRedirection.
PipeRedirectionBase* NewPipeRedir() PipeRedirectionBase* NewPipeRedir( FILE* stdstream )
{ {
return new WinPipeRedirection(); try
{
return new WinPipeRedirection( stdstream );
}
catch( Exception::RuntimeError& ex )
{
// Entirely non-critical errors. Log 'em and move along.
Console::Error( ex.FormatDiagnosticMessage() );
}
return NULL;
} }