Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
19 commits
Select commit Hold shift + click to select a range
d9f9856
ファイルダイアログへの入力をファイル名のみにするのをやめる
berryzplus Jul 17, 2026
5e57a59
WinMainTestのウィンドウ待機を強化する
berryzplus Jul 17, 2026
67ffccb
cxx::HandleHolderを再定義する
berryzplus Jul 17, 2026
eb57fff
WinMainFuncTestでもStartWindowCloserを使う
berryzplus Jul 17, 2026
6b734eb
テストにcxx::ProcessHolderを導入する
berryzplus Jul 17, 2026
8b7b482
コントロールプロセス初期化の完了待機を改善する(1/2)
berryzplus Jul 17, 2026
d0eb08c
コントロールプロセス初期化の完了待機を改善する(2/2)
berryzplus Jul 17, 2026
ae2c158
エディタ-初期化完了イベントを導入する
berryzplus Jul 17, 2026
34f4e49
テストにcxx::EditorProcessHolderを導入する
berryzplus Jul 17, 2026
06b1af9
SonarQube指摘対応 Use the init-statement
berryzplus Jul 17, 2026
b350b82
SonarQube指摘対応 This function should be declared "const".
berryzplus Jul 17, 2026
7f7a8aa
SonarQube指摘対応 Remove this redundant access specifier
berryzplus Jul 17, 2026
0668d9b
CNormalProcess::OpenFilesを同期に変える
berryzplus Jul 17, 2026
fce2434
エディター初期化完了イベントの検出をアプリ側に組み込む
berryzplus Jul 17, 2026
77d5852
SonarQube指摘対応 This function should be declared "const".
berryzplus Jul 17, 2026
18bc85f
SonarQube指摘対応でCNormalProcess::OpenFilesを組み直す
berryzplus Jul 17, 2026
2409e20
SonarQube指摘対応 Make sure use of "wcscpy" is safe here.
berryzplus Jul 17, 2026
66a00cc
SonarQube指摘対応 Use the init-statement
berryzplus Jul 17, 2026
e0e0fe7
SonarQube指摘対応 Make the type of this variable a pointer-to-const.
berryzplus Jul 17, 2026
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
25 changes: 7 additions & 18 deletions sakura_core/_main/CControlProcess.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@
Copyright (C) 2002, aroka CProcessより分離, YAZAKI
Copyright (C) 2006, ryoji
Copyright (C) 2007, ryoji
Copyright (C) 2018-2022, Sakura Editor Organization
Copyright (C) 2018-2026, Sakura Editor Organization

This source code is designed for sakura editor.
Please contact the copyright holder to use this code for other purpose.
Expand Down Expand Up @@ -130,16 +130,13 @@ bool CControlProcess::InitializeProcess()

const auto pszProfileName = GetProfileName();

// 初期化完了イベントを作成する
// 初期化完了イベントの名前を組み立てる
std::wstring strInitEvent = GSTR_EVENT_SAKURA_CP_INITIALIZED;
strInitEvent += pszProfileName;
m_hEventCPInitialized = ::CreateEvent( nullptr, TRUE, FALSE, strInitEvent.c_str() );
if( nullptr == m_hEventCPInitialized )
{
ErrorBeep();
TopErrorMessage( nullptr, L"CreateEvent()失敗。\n終了します。" );
return false;
}

// 起動元が作成した初期化完了イベントを開く。
using HandleHolder = cxx::ResourceHolder<&::CloseHandle>;
HandleHolder hEvent{ ::OpenEventW(EVENT_MODIFY_STATE, FALSE, std::data(strInitEvent)) };

/* コントロールプロセスの目印 */
std::wstring strCtrlProcEvent = GSTR_MUTEX_SAKURA_CP;
Expand Down Expand Up @@ -194,11 +191,7 @@ bool CControlProcess::InitializeProcess()
GetDllShareData().m_sHandles.m_hwndTray = hwnd;

// 初期化完了イベントをシグナル状態にする
if( !::SetEvent( m_hEventCPInitialized ) ){
ErrorBeep();
TopErrorMessage( nullptr, LS(STR_ERR_CTRLMTX4) );
return false;
}
if (hEvent) ::SetEvent(hEvent);

return true;
}
Expand Down Expand Up @@ -234,10 +227,6 @@ CControlProcess::~CControlProcess()
{
delete m_pcTray;

if( m_hEventCPInitialized ){
::ResetEvent( m_hEventCPInitialized );
}
::CloseHandle( m_hEventCPInitialized );
if( m_hMutexCP ){
::ReleaseMutex( m_hMutexCP );
}
Expand Down
4 changes: 2 additions & 2 deletions sakura_core/_main/CControlProcess.h
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@
/*
Copyright (C) 2002, aroka 新規作成, YAZAKI
Copyright (C) 2006, ryoji
Copyright (C) 2018-2022, Sakura Editor Organization
Copyright (C) 2018-2026, Sakura Editor Organization

This source code is designed for sakura editor.
Please contact the copyright holder to use this code for other purpose.
Expand Down Expand Up @@ -55,7 +55,7 @@ class CControlProcess final : public CProcess {

HANDLE m_hMutex = nullptr; //!< アプリケーション実行検出用ミューテックス
HANDLE m_hMutexCP = nullptr; //!< コントロールプロセスミューテックス
HANDLE m_hEventCPInitialized = nullptr; //!< コントロールプロセス初期化完了イベント 2006.04.10 ryoji
CControlTray* m_pcTray = nullptr;
};

#endif /* SAKURA_CCONTROLPROCESS_AFB90808_4287_4A11_B7FB_9CD21CF8BFD6_H_ */
104 changes: 49 additions & 55 deletions sakura_core/_main/CControlTray.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -65,6 +65,18 @@
/////////////////////////////////////////////////////////////////////////
static LRESULT CALLBACK CControlTrayWndProc( HWND, UINT, WPARAM, LPARAM );

namespace cxx {

/*!
* @brief トップレベルウインドウを検索する
*/
HWND FindWindowW(std::wstring_view className, const std::optional<std::wstring>& optWindowName = std::nullopt)
{
return ::FindWindowW(std::data(std::wstring(className)), optWindowName.has_value() ? std::data(*optWindowName) : nullptr);
}

} // namespace cxx

//Stonee, 2001/03/21
//Stonee, 2001/07/01 多重起動された場合は前回のダイアログを前面に出すようにした。
void CControlTray::DoGrep()
Expand Down Expand Up @@ -221,8 +233,7 @@ HWND CControlTray::Create( HINSTANCE hInstance )
const auto pszProfileName = GetProfileName();
std::wstring strCEditAppName = GSTR_CEDITAPP;
strCEditAppName += pszProfileName;
HWND hwndWork = ::FindWindow( strCEditAppName.c_str(), strCEditAppName.c_str() );
if( nullptr != hwndWork ){
if (const auto hWndTray = cxx::FindWindowW(strCEditAppName, strCEditAppName); hWndTray){
return nullptr;
}

Expand Down Expand Up @@ -277,7 +288,7 @@ HWND CControlTray::Create( HINSTANCE hInstance )
m_pcPropertyManager = new CPropertyManager();
m_pcPropertyManager->Create( GetTrayHwnd(), &m_hIcons, &m_cMenuDrawer );

wcscpy(m_szLanguageDll, GetDllShareData().m_Common.m_sWindow.m_szLanguageDll);
m_szLanguageDll = GetDllShareData().m_Common.m_sWindow.m_szLanguageDll;

return GetTrayHwnd();
}
Expand Down Expand Up @@ -320,7 +331,7 @@ bool CControlTray::CreateTrayIcon( [[maybe_unused]] HWND hWnd )
}

/* メッセージループ */
void CControlTray::MessageLoop( void )
void CControlTray::MessageLoop() const
{
//複数プロセス版
MSG msg;
Expand All @@ -338,7 +349,7 @@ void CControlTray::MessageLoop( void )
}

/* タスクトレイのアイコンに関する処理 */
BOOL CControlTray::TrayMessage( HWND hDlg, DWORD dwMessage, UINT uID, HICON hIcon, const WCHAR* pszTip )
BOOL CControlTray::TrayMessage(HWND hDlg, DWORD dwMessage, UINT uID, HICON hIcon, const WCHAR* pszTip) const
{
BOOL res;
NOTIFYICONDATA tnd;
Expand Down Expand Up @@ -577,7 +588,7 @@ LRESULT CControlTray::DispatchEvent(
}
{
bool bChangeLang = wcscmp( GetDllShareData().m_Common.m_sWindow.m_szLanguageDll, m_szLanguageDll ) != 0;
wcscpy( m_szLanguageDll, GetDllShareData().m_Common.m_sWindow.m_szLanguageDll );
m_szLanguageDll = GetDllShareData().m_Common.m_sWindow.m_szLanguageDll;
std::vector<std::wstring> values;
if( bChangeLang ){
CShareData::getInstance()->ConvertLangValues(values, true);
Expand Down Expand Up @@ -947,7 +958,7 @@ LRESULT CControlTray::DispatchEvent(
}

/* WM_COMMANDメッセージ処理 */
void CControlTray::OnCommand( WORD wNotifyCode, [[maybe_unused]] WORD wID , [[maybe_unused]] HWND hwndCtl )
void CControlTray::OnCommand(WORD wNotifyCode, [[maybe_unused]] WORD wID , [[maybe_unused]] HWND hwndCtl) const
{
switch( wNotifyCode ){
/* メニューからのメッセージ */
Expand Down Expand Up @@ -1114,10 +1125,10 @@ bool CControlTray::OpenNewEditor(
)
{
/* 共有データ構造体のアドレスを返す */
DLLSHAREDATA* pShareData = &GetDllShareData();
const auto pShareData = &GetDllShareData();

/* 編集ウィンドウの上限チェック */
if( pShareData->m_sNodes.m_nEditArrNum >= MAX_EDITWINDOWS ){ //最大値修正 //@@@ 2003.05.31 MIK
if (MAX_EDITWINDOWS <= pShareData->m_sNodes.m_nEditArrNum) {
OkMessage( nullptr, LS(STR_MAXWINDOW), MAX_EDITWINDOWS );
return false;
}
Expand Down Expand Up @@ -1228,11 +1239,15 @@ bool CControlTray::OpenNewEditor(
// May 30, 2003 genta カレントディレクトリ指定を可能に
//エディタプロセスを起動
DWORD dwCreationFlag = CREATE_DEFAULT_ERROR_MODE;

if (sync) dwCreationFlag |= CREATE_SUSPENDED;

#ifdef _DEBUG
// dwCreationFlag |= DEBUG_PROCESS; //2007.09.22 kobake デバッグ用フラグ
#endif
WCHAR szCmdLine[1024]; wcscpy_s(szCmdLine, std::size(szCmdLine), cCmdLineBuf.c_str());
BOOL bCreateResult = CreateProcess(

if (const auto bCreateResult = ::CreateProcessW(
szEXE, // 実行可能モジュールの名前
szCmdLine, // コマンドラインの文字列
nullptr, // セキュリティ記述子
Expand All @@ -1244,7 +1259,7 @@ bool CControlTray::OpenNewEditor(
&s, // スタートアップ情報
&p // プロセス情報
);
if( !bCreateResult ){
!bCreateResult) {
// 失敗
WCHAR* pMsg;
FormatMessage( FORMAT_MESSAGE_ALLOCATE_BUFFER |
Expand All @@ -1267,11 +1282,28 @@ bool CControlTray::OpenNewEditor(
return false;
}

// タブまとめ時は起動したプロセスが立ち上がるまでしばらくタイトルバーをアクティブに保つため、強制的に同期モードにする
if (pShareData->m_Common.m_sTabBar.m_bDispTabWnd && !pShareData->m_Common.m_sTabBar.m_bDispTabWndMultiWin && !sync){
sync = true;
}

// MYWM_FIRST_IDLE が届くまでちょっとだけ余分に待つ // 2008.04.19 ryoji
// Note. 起動先プロセスが初期化処理中に COM 関数(SHGetFileInfo API なども含む)を実行すると、
// その時点で COM の同期機構が動いて WaitForInputIdle は終了してしまう可能性がある(らしい)。
bool bRet = true;
if( sync ){
// 起動したプロセスが完全に立ち上がるまでちょっと待つ.
int nResult = WaitForInputIdle( p.hProcess, 10000 ); // 最大10秒間待つ
if( nResult != 0 ){
if (sync)
{
// エディター初期化完了イベントを作成する
SFilePath initEventName{ std::format(GSTR_EVENT_SAKURA_EP_INITIALIZED, p.dwThreadId) };
HANDLE hEvent = ::CreateEventW(nullptr, TRUE, FALSE, initEventName);

// エディターのメインスレッドを再開する
::ResumeThread(p.hThread);

// エディター初期化完了を待つ
std::array handles{ hEvent, p.hProcess };
const auto dwRet = ::WaitForMultipleObjects(DWORD(std::size(handles)), std::data(handles), FALSE, 15000);
if (WAIT_OBJECT_0 != dwRet) {
ErrorMessage(
hWndParent,
LS(STR_TRAY_CREATEPROC2),
Expand All @@ -1280,40 +1312,6 @@ bool CControlTray::OpenNewEditor(
bRet = false;
}
}
else{
// タブまとめ時は起動したプロセスが立ち上がるまでしばらくタイトルバーをアクティブに保つ // 2007.02.03 ryoji
if( pShareData->m_Common.m_sTabBar.m_bDispTabWnd && !pShareData->m_Common.m_sTabBar.m_bDispTabWndMultiWin ){
WaitForInputIdle( p.hProcess, 3000 );
sync = true;
}
}

// MYWM_FIRST_IDLE が届くまでちょっとだけ余分に待つ // 2008.04.19 ryoji
// Note. 起動先プロセスが初期化処理中に COM 関数(SHGetFileInfo API なども含む)を実行すると、
// その時点で COM の同期機構が動いて WaitForInputIdle は終了してしまう可能性がある(らしい)。
if( sync && bRet )
{
int i;
for( i = 0; i < 200; i++ ){
MSG msg;
DWORD dwExitCode;
if( ::PeekMessage( &msg, nullptr, MYWM_FIRST_IDLE, MYWM_FIRST_IDLE, PM_REMOVE ) ){
if( msg.message == WM_QUIT ){ // 指定範囲外でも WM_QUIT は取り出される
::PostQuitMessage( int(msg.wParam) );
break;
}
// 監視対象プロセスからのメッセージなら抜ける
// そうでなければ破棄して次を取り出す
if( msg.wParam == p.dwProcessId ){
break;
}
}
if( ::GetExitCodeProcess( p.hProcess, &dwExitCode ) && dwExitCode != STILL_ACTIVE ){
break; // 監視対象プロセスが終了した
}
::Sleep(10);
}
}

CloseHandle( p.hThread );
CloseHandle( p.hProcess );
Expand All @@ -1335,13 +1333,9 @@ bool CControlTray::OpenNewEditor2(
bool bNewWindow //!< [in] 新規エディタを新しいウインドウで開く
)
{
DLLSHAREDATA* pShareData;

/* 共有データ構造体のアドレスを返す */
pShareData = &GetDllShareData();

/* 編集ウィンドウの上限チェック */
if( pShareData->m_sNodes.m_nEditArrNum >= MAX_EDITWINDOWS ){ //最大値修正 //@@@ 2003.05.31 MIK
if (const auto pShareData = &GetDllShareData();
MAX_EDITWINDOWS <= pShareData->m_sNodes.m_nEditArrNum) {
OkMessage( nullptr, LS(STR_MAXWINDOW), MAX_EDITWINDOWS );
return false;
}
Expand Down
6 changes: 3 additions & 3 deletions sakura_core/_main/CControlTray.h
Original file line number Diff line number Diff line change
Expand Up @@ -73,7 +73,7 @@ class CControlTray
HWND Create(HINSTANCE hInstance); /* 作成 */
bool CreateTrayIcon(HWND hWnd); // 20010412 by aroka
LRESULT DispatchEvent(HWND hWnd, UINT Msg, WPARAM wParam, LPARAM lParam); /* メッセージ処理 */
void MessageLoop( void ); /* メッセージループ */
void MessageLoop() const; /* メッセージループ */
void OnDestroy( void ); /* WM_DESTROY 処理 */ // 2006.07.09 ryoji
int CreatePopUpMenu_L( void ); /* ポップアップメニュー(トレイ左ボタン) */
int CreatePopUpMenu_R( void ); /* ポップアップメニュー(トレイ右ボタン) */
Expand Down Expand Up @@ -111,8 +111,8 @@ class CControlTray
static void DoGrepCreateWindow(HINSTANCE hinst, HWND, CDlgGrep& cDlgGrep);
protected:
void DoGrep(); //Stonee, 2001/03/21
BOOL TrayMessage(HWND hDlg, DWORD dwMessage, UINT uID, HICON hIcon, const WCHAR* pszTip); /*!< タスクトレイのアイコンに関する処理 */
void OnCommand(WORD wNotifyCode, WORD wID, HWND hwndCtl); /*!< WM_COMMANDメッセージ処理 */
BOOL TrayMessage(HWND hDlg, DWORD dwMessage, UINT uID, HICON hIcon, const WCHAR* pszTip) const; /*!< タスクトレイのアイコンに関する処理 */
void OnCommand(WORD wNotifyCode, WORD wID, HWND hwndCtl) const; /*!< WM_COMMANDメッセージ処理 */
void OnNewEditor(bool bNewWindow); //!< 2003.05.30 genta 新規ウィンドウ作成処理を切り出し

static INT_PTR CALLBACK ExitingDlgProc( /*!< 終了ダイアログ用プロシージャ */ // 2006.07.02 ryoji CControlProcess から移動
Expand Down
Loading
Loading