⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 nt_service.hpp

📁 j2me is based on j2mepolish, client & server for mobile application.
💻 HPP
📖 第 1 页 / 共 2 页
字号:
		BOOL ret = ::QueryServiceConfig(handle_, 0, 
			0, &BytesNeeded);

		assert (!ret && GetLastError() == ERROR_INSUFFICIENT_BUFFER);

		boost::shared_array<BYTE> qsc(new BYTE[BytesNeeded]);

		ret = ::QueryServiceConfig(handle_, (LPQUERY_SERVICE_CONFIG)qsc.get(), 
			BytesNeeded, &BytesNeeded);

		if (!ret) throw_nt_service_exception(lpServiceName_.c_str());

		assert(ret);
		return qsc;
	}

	std::pair<DWORD, t_string> dwServiceType(SERVICE_STATUS_PROCESS* ssp = 0) const
	{
		DWORD flags;
		t_string str;

		if (ssp)
			flags = ssp->dwServiceType;
		else
		{
			assert (dwDesiredAccess_ & SERVICE_QUERY_STATUS);
			flags = QueryServiceStatus().dwServiceType;
		}

		if (flags & SERVICE_FILE_SYSTEM_DRIVER)
			str = L"Filesystem Driver";
		else if (flags & SERVICE_KERNEL_DRIVER)
			str = L"Device Driver";
		else if (flags & SERVICE_WIN32_OWN_PROCESS)
			str = L"Standalone Service";
		else if (flags & SERVICE_WIN32_SHARE_PROCESS)
			str = L"Shared Process Service";

		if (flags & SERVICE_INTERACTIVE_PROCESS)
			str += L", interactive";

		return std::make_pair(flags, str);
	}

	std::pair<DWORD, t_string> dwCurrentState(SERVICE_STATUS_PROCESS* ssp = 0) const
	{
		DWORD flags;
		t_string str;

		if (ssp)
			flags = ssp->dwCurrentState;
		else
		{
			assert (dwDesiredAccess_ & SERVICE_QUERY_STATUS);
			flags = QueryServiceStatus().dwCurrentState;
		}

		return std::make_pair(flags, dwCurrentState_to_string(flags));
	}

	std::pair<DWORD, t_string> dwStartType(boost::shared_array<BYTE> qsc = boost::shared_array<BYTE>()) const
	{
		DWORD flags;
		t_string str;

		if (qsc)
			flags = ((LPQUERY_SERVICE_CONFIG)qsc.get())->dwStartType;
		else
		{
			assert (dwDesiredAccess_ & SERVICE_QUERY_CONFIG);
			flags = ((LPQUERY_SERVICE_CONFIG)QueryServiceConfig().get())->dwStartType;
		}

		return std::make_pair(flags,  dwStartType_to_string(flags));
	}

	t_string lpServiceStartName(boost::shared_array<BYTE> qsc = boost::shared_array<BYTE>()) const
	{
		if (qsc)
			return t_string(((LPQUERY_SERVICE_CONFIG)qsc.get())->lpServiceStartName);
		else
		{
			assert (dwDesiredAccess_ & SERVICE_QUERY_CONFIG);
			return t_string(((LPQUERY_SERVICE_CONFIG)QueryServiceConfig().get())->lpServiceStartName);
		}
	}

	t_string lpBinaryPathName(boost::shared_array<BYTE> qsc = boost::shared_array<BYTE>()) const
	{
		if (qsc)
			return t_string(((LPQUERY_SERVICE_CONFIG)qsc.get())->lpBinaryPathName);
		else
		{
			assert (dwDesiredAccess_ & SERVICE_QUERY_CONFIG);
			return t_string(((LPQUERY_SERVICE_CONFIG)QueryServiceConfig().get())->lpBinaryPathName);
		}
	}

	t_string lpDescription() const
	{
		assert (dwDesiredAccess_ | SERVICE_QUERY_CONFIG);

		DWORD BytesNeeded = 0;

		BOOL ret = ::QueryServiceConfig2(handle_, SERVICE_CONFIG_DESCRIPTION, 0, 
			0, &BytesNeeded);

		assert (!ret && GetLastError() == ERROR_INSUFFICIENT_BUFFER);

		boost::shared_array<BYTE> qsc(new BYTE[BytesNeeded]);

		ret = ::QueryServiceConfig2(handle_, SERVICE_CONFIG_DESCRIPTION, (LPBYTE)qsc.get(), 
			BytesNeeded, &BytesNeeded);

		if (!ret) throw_nt_service_exception(lpServiceName_.c_str());

		if ((DWORD)*qsc.get() != 0)
			return t_string(((LPSERVICE_DESCRIPTION)qsc.get())->lpDescription);
		else
			return t_string();
	}

	bool ApplySettings(const service_settings& svc_s)
	{
		BOOL result = true;

		std::pair<DWORD, t_string> st = dwStartType();

		if (st.first != svc_s.dwStartType_)
		{
			if (!(dwDesiredAccess_ & SERVICE_CHANGE_CONFIG))
				aquire_permission(SERVICE_CHANGE_CONFIG);

			result = ::ChangeServiceConfig(handle_, SERVICE_NO_CHANGE, svc_s.dwStartType_, SERVICE_NO_CHANGE, 
				NULL, NULL, NULL, NULL, NULL, NULL, NULL);
		
			if (!result) throw_nt_service_exception(lpServiceName_.c_str());
		}

		std::pair<DWORD, t_string> cs = dwCurrentState();

		switch (svc_s.dwCurrentState_)
		{
		case SERVICE_RUNNING:
			result = Start();
			break;

		case SERVICE_STOPPED:
			result = Stop();
			break;

		case SERVICE_PAUSED:
			result = Pause();
			break;
		}

		return result ? true : false;
	}

	BOOL Start()
	{
		aux::wlog() << L"Service start requested";

		std::pair<DWORD, t_string> cs = dwCurrentState();

		if (cs.first == SERVICE_RUNNING ||
				cs.first == SERVICE_START_PENDING ||
				cs.first == SERVICE_CONTINUE_PENDING)
		{
			aux::wlog() << L"Already started";
			return true;
		}

		if (!(dwDesiredAccess_ & SERVICE_START))
			aquire_permission(SERVICE_START);

		aux::wlog() << L"Making start request...";
		BOOL result = ::StartService(handle_, NULL, NULL);
		aux::wlog() << boost::wformat(L"... request %1%") % (result ? L"succeeded" : L"failed");
		
		if (!result) throw_nt_service_exception(lpServiceName_.c_str());

		return result;
	}

	BOOL Stop()
	{
		aux::wlog() << L"Service stop requested";

		std::pair<DWORD, t_string> cs = dwCurrentState();

		if (cs.first == SERVICE_STOPPED ||
				cs.first == SERVICE_STOP_PENDING)
		{
			aux::wlog() << L"Already stopped";
			return true;
		}

		if (!(dwDesiredAccess_ & SERVICE_STOP))
			aquire_permission(SERVICE_STOP);

		aux::wlog() << L"Making stop request...";
		SERVICE_STATUS ss;
		BOOL result = ::ControlService(handle_, SERVICE_CONTROL_STOP, &ss);
		aux::wlog() << boost::wformat(L"... request %1%") % (result ? L"succeeded" : L"failed");
		
		if (!result) throw_nt_service_exception(lpServiceName_.c_str());

		return result;
	}

	BOOL Pause()
	{
		aux::wlog() << L"Service pause requested";

		std::pair<DWORD, t_string> cs = dwCurrentState();

		if (cs.first == SERVICE_PAUSED ||
				cs.first == SERVICE_PAUSE_PENDING)
		{
			aux::wlog() << L"Already paused";
			return true;
		}
		else if (cs.first == SERVICE_STOPPED ||
				cs.first == SERVICE_STOP_PENDING)
		{
			aux::wlog() << L"Already stopped, not going to pause";
			return true;
		}

		if (!(dwDesiredAccess_ & SERVICE_PAUSE_CONTINUE))
			aquire_permission(SERVICE_PAUSE_CONTINUE);

		aux::wlog() << L"Making pause request...";
		SERVICE_STATUS ss;
		BOOL result = ::ControlService(handle_, SERVICE_CONTROL_PAUSE, &ss);
		aux::wlog() << boost::wformat(L"... request %1%") % (result ? L"succeeded" : L"failed");
		
		if (!result) throw_nt_service_exception(lpServiceName_.c_str());

		return result;
	}

	static t_string dwStartType_to_string(DWORD StartType)
	{	
		if (StartType == SERVICE_AUTO_START)
			return L"Automatic";
		else if (StartType == SERVICE_BOOT_START)
			return L"Boot Start";
		else if (StartType == SERVICE_DEMAND_START)
			return L"Manual";
		else if (StartType == SERVICE_DISABLED)
			return L"Disabled";
		else if (StartType == SERVICE_SYSTEM_START)
			return L"System Start";
		else if (StartType == SERVICE_NO_CHANGE)
			return L"(no change)";
		else
			return L"?No Start Type?";
	}

	static t_string dwCurrentState_to_string(DWORD CurrentState)
	{
		if (CurrentState == SERVICE_CONTINUE_PENDING)
			return L"Continue";
		else if (CurrentState == SERVICE_PAUSE_PENDING)
			return L"Pause pending";
		else if (CurrentState == SERVICE_PAUSED)
			return L"Paused";
		else if (CurrentState == SERVICE_RUNNING)
			return L"Running";
		else if (CurrentState == SERVICE_START_PENDING)
			return L"Start pending";
		else if (CurrentState == SERVICE_STOP_PENDING)
			return L"Stop pending";
		else if (CurrentState == SERVICE_NO_CHANGE)
			return L"(no change)";
		else if (CurrentState == SERVICE_STOPPED)
			return L"Stopped";
		else
			return L"?No State?";
	}

private:
	void aquire_permission(DWORD permission)
	{
		aux::wlog() << L"Trying to get access...";

		SC_HANDLE handle = OpenService(*manager_, lpServiceName_.c_str(), dwDesiredAccess_|permission);
		if (!handle) throw_nt_service_exception(lpServiceName_.c_str());
		
		aux::wlog() << L"Succeeded";
		::CloseServiceHandle(handle_);
		handle_ = handle;
		dwDesiredAccess_ |= permission;
	}

	SC_HANDLE handle_;

	nt_service_control_manager_ptr manager_;

	t_string lpServiceName_;
	DWORD dwDesiredAccess_;
};

typedef boost::shared_ptr<nt_service> service_ptr;

#endif // NT_SERVICE_HPP_INCLUDED

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -