Chinaunix首页 | 论坛 | 博客
  • 博客访问: 609430
  • 博文数量: 945
  • 博客积分: 52360
  • 博客等级: 大将
  • 技术积分: 13070
  • 用 户 组: 普通用户
  • 注册时间: 2008-08-08 11:12
文章分类

全部博文(945)

文章存档

2011年(1)

2008年(944)

我的朋友

分类: C/C++

2008-08-08 11:32:14

下载本文示例代码
下载示例源代码

单位最近加强安全检查,除了部分服务器,下班不关机器的同事,都被罚了款。为此,我试着下载了几个自动关机的程序,但是都不好使。都是最后显示“你可以安全地关闭计算机了!”。到网上问了半天说是高级电源管理设置的问题。我折腾了半天,还是不行,为什么Windows自己的关机就可以关掉电源,而我们的程序就只能“你可以安全的关闭计算了!”。看来微软还不知道在哪里留了一手。
好在还有收获,最近发现MSDN还有这么一个函数
BOOL SetSystemPowerState(

  BOOL fSuspend,  // system state

  BOOL fForce     // forced suspension option

);
真是好东东,比关机器还好,在任何情况下都可以切断电源(这正是我想要的),也不会有讨厌的提示。

函数很简单,但直接用不好使,前面得加些罗哩八嗦的东东,所以我就进行了一下封装。

void  PERR(LPTSTR szAPI, DWORD dwLastError);

#define RTN_ERROR 13



INT SetPower()

{

	

	// TODO: Add your control notificationhandler code here

   TOKEN_PRIVILEGES tp;

    HANDLE hToken;

	LUID luid;



   LPTSTR MachineName=NULL; // pointer to machine name



	if(!OpenProcessToken(GetCurrentProcess(),

                        TOKEN_ADJUST_PRIVILEGES,

                        &hToken ))

    {

        PERR("OpenProcessToken", GetLastError() );

        return RTN_ERROR;

    }



    if(!LookupPrivilegeValue(MachineName, SE_SHUTDOWN_NAME, &luid))



    {

        PERR("LookupPrivilegeValue", GetLastError() );

        return RTN_ERROR;

    }



    tp.PrivilegeCount           = 1;

    tp.Privileges[0].Luid       = luid;

    tp.Privileges[0].Attributes = SE_PRIVILEGE_ENABLED;



    AdjustTokenPrivileges(hToken, FALSE, &tp, sizeof(TOKEN_PRIVILEGES),

                                NULL, NULL );



        SetSystemPowerState(FALSE,TRUE);			    

		return 0;



}
void PERR(

    LPTSTR szAPI,       // pointer to failed API name

    DWORD dwLastError   // last error value associated with API

    )

{

    LPTSTR MessageBuffer;

    DWORD dwBufferLength;



    // 

    // TODO get this fprintf out of here!

    // 

    fprintf(stderr,"%s error! (rc=%lu)\n", szAPI, dwLastError);



    if(dwBufferLength=FormatMessage(FORMAT_MESSAGE_ALLOCATE_BUFFER |

                                    FORMAT_MESSAGE_FROM_SYSTEM,

                                    NULL,

                                    dwLastError,

                                    LANG_NEUTRAL,

                                    (LPTSTR) &MessageBuffer,

                                    0,

                                    NULL))

    {



        DWORD dwBytesWritten;



        // 

        // Output message string on stderr

        // 

        WriteFile(GetStdHandle(STD_ERROR_HANDLE),

                  MessageBuffer,

                  dwBufferLength,

                  &dwBytesWritten,

                  NULL);



        // 

        // free the buffer allocated by the system

        // 

        LocalFree(MessageBuffer);

    }

}

注意:此函数只运行于Windows 2000/XP,并且打开了高级电源管理的休眠支持。

根据这个函数,写了个小东东,我不想让他一直运行占我的资源。于是就在计划任务里建了一个任务,只要在检查之前执行就行。呵呵!
总之没什么高深的,我也是菜鸟,如果你知道了就不要看了,希望那些爱骂人“高手”不要骂我:-) 下载本文示例代码
阅读(81) | 评论(0) | 转发(0) |
给主人留下些什么吧!~~