void BrowserFactory::LaunchBrowserUsingIELaunchURL(const std::string& initial_url, PROCESS_INFORMATION* proc_info, std::string* error_message) { LOG(TRACE) << "Entering BrowserFactory::IsIELaunchURLAvailable"; LOG(DEBUG) << "Starting IE using the IELaunchURL API"; std::wstring wide_initial_url = StringUtilities::ToWString(initial_url); HRESULT launch_result = ::IELaunchURL(wide_initial_url.c_str(), proc_info, NULL); if (FAILED(launch_result)) { size_t launch_msg_count = _scprintf(IELAUNCHURL_ERROR_MESSAGE, launch_result, initial_url.c_str()); vector<char> launch_result_msg(launch_msg_count + 1); _snprintf_s(&launch_result_msg[0], launch_result_msg.size(), launch_msg_count + 1, IELAUNCHURL_ERROR_MESSAGE, launch_result, initial_url.c_str()); std::string launch_error = &launch_result_msg[0]; *error_message = launch_error; } }
DWORD BrowserFactory::LaunchBrowserProcess(const std::string& initial_url, const bool ignore_protected_mode_settings, std::string* error_message) { LOG(TRACE) << "Entering BrowserFactory::LaunchBrowserProcess"; DWORD process_id = NULL; bool has_valid_protected_mode_settings = false; LOG(DEBUG) << "Ignoring Protected Mode Settings: " << ignore_protected_mode_settings; if (!ignore_protected_mode_settings) { LOG(DEBUG) << "Checking validity of Protected Mode settings."; has_valid_protected_mode_settings = this->ProtectedModeSettingsAreValid(); } LOG(DEBUG) << "Has Valid Protected Mode Settings: " << has_valid_protected_mode_settings; if (ignore_protected_mode_settings || has_valid_protected_mode_settings) { STARTUPINFO start_info; PROCESS_INFORMATION proc_info; ::ZeroMemory(&start_info, sizeof(start_info)); start_info.cb = sizeof(start_info); ::ZeroMemory(&proc_info, sizeof(proc_info)); std::wstring wide_initial_url(CA2W(initial_url.c_str(), CP_UTF8)); FARPROC proc_address = 0; HMODULE library_handle = ::LoadLibrary(IEFRAME_LIBRARY_NAME); if (library_handle != NULL) { proc_address = ::GetProcAddress(library_handle, IELAUNCHURL_FUNCTION_NAME); } std::string launch_api = "The IELaunchURL() API"; std::string launch_error = ""; if (proc_address != 0) { // If we have the IELaunchURL API, expressly use it. This will // guarantee a new session. Simply using CoCreateInstance to // create the browser will merge sessions, making separate cookie // handling impossible. HRESULT launch_result = ::IELaunchURL(wide_initial_url.c_str(), &proc_info, NULL); if (FAILED(launch_result)) { size_t launch_msg_count = _scprintf(IELAUNCHURL_ERROR_MESSAGE, launch_result, initial_url); vector<char> launch_result_msg(launch_msg_count + 1); _snprintf_s(&launch_result_msg[0], sizeof(launch_result_msg), launch_msg_count + 1, IELAUNCHURL_ERROR_MESSAGE, launch_result, initial_url); launch_error = &launch_result_msg[0]; *error_message = launch_error; } } else { launch_api = "The CreateProcess() API"; std::wstring executable_and_url = this->ie_executable_location_ + L" " + wide_initial_url; LPWSTR command_line = new WCHAR[executable_and_url.size() + 1]; wcscpy_s(command_line, executable_and_url.size() + 1, executable_and_url.c_str()); command_line[executable_and_url.size()] = L'\0'; BOOL create_process_result = ::CreateProcess(NULL, command_line, NULL, NULL, FALSE, 0, NULL, NULL, &start_info, &proc_info); if (!create_process_result) { int create_proc_msg_count = _scwprintf(CREATEPROCESS_ERROR_MESSAGE, command_line); vector<wchar_t> create_proc_result_msg(create_proc_msg_count + 1); _snwprintf_s(&create_proc_result_msg[0], sizeof(create_proc_result_msg), create_proc_msg_count, CREATEPROCESS_ERROR_MESSAGE, command_line); launch_error = CW2A(&create_proc_result_msg[0], CP_UTF8); *error_message = launch_error; } delete[] command_line; } process_id = proc_info.dwProcessId; if (process_id == NULL) { // If whatever API we are using failed to launch the browser, we should // have a NULL value in the dwProcessId member of the PROCESS_INFORMATION // structure. In that case, we will have already set the approprate error // message. On the off chance that we haven't yet set the appropriate // error message, that means we successfully launched the browser (i.e., // the browser launch API returned a success code), but we still have a // NULL process ID. if (launch_error.size() == 0) { *error_message = launch_api + NULL_PROCESS_ID_ERROR_MESSAGE; } } if (proc_info.hThread != NULL) { ::CloseHandle(proc_info.hThread); } if (proc_info.hProcess != NULL) { ::CloseHandle(proc_info.hProcess); } if (library_handle != NULL) { ::FreeLibrary(library_handle); } } else { *error_message = PROTECTED_MODE_SETTING_ERROR_MESSAGE; } return process_id; }