摘要:有些笔记本腾达路由器密码破解在使用中发出一种高频路由器登陆密码破解电流噪音。这种噪音随无线路由器密码破解着硬盘的读写,用户对飞鹤奶粉价格拉动发生变化,并在操[url=http://maigoo.com/company/4842.html]飞鹤奶粉怎么样[/url动发生变化,并在操作系统启动之后几乎始终存在,只有当用户播放音频文件时这种噪音会消失。本文利用这一特点针对Windows操作系统给出了消除噪音解决方案。本文设计了一个占用资源较少的Windows系统服务,在里面模拟音频文件的播放,从而将噪音消除。 关键字:笔记本高频电流噪音 Windows系统服务  问题分析 有些笔记本由于设计方面的问题,如果使用了USB设备或蓝牙模块,在运行中会发出一种高频电流噪音。例子包括Dell D610,Think R60e(在使用电池的模式下)。这种噪音的来源并未得到官方的解释。但是有些厂商已经发布了修复这种噪音问题的BIOS补丁[1]。但是某些厂商并未正面解决这个问题[2]。 有一种比较方便易行的方法可以把这种噪音消除:播放一个音频文件,然后按下暂停按钮。某些用户反映在运行一些游戏时也可以将噪音消除,其实也是利用了游戏背景音乐的作用。但是这种方法的缺点是需要手工操作,并且音乐播放器往往占用大量的内存。我们应该考虑用一种节省的方式实现它。 设计与实现 Windows提供了一组波形音频的编程接口。我们可以利用它们模拟播放器的暂停状态: //代码: 模拟播放器的暂停状态HWAVEOUT hWaveOut;          //波形音频输出句柄BYTE mute[MUTE_LENGTH];     //静音符号串WAVEFORMATEX waveformat = { 
    WAVE_FORMAT_PCM, 1, SAMPLE_RATE, SAMPLE_RATE, 1, 8, 0 
};                          //设定波形音频的格式WAVEHDR waveHdr = { 
    0, MUTE_LENGTH, 0, 0, 0, 1, NULL, 0 
};                          //音频数据信息头 
FillMemory(mute, MUTE_LENGTH, (BYTE)0x80);  //用静音符号填充waveHdr.lpData = mute;                      //初始化信息头指针 
//打开音频设备waveOutOpen (&hWaveOut, WAVE_MAPPER, &waveformat, 0, 0, CALLBACK_FUNCTION); 
//准备信息头waveOutPrepareHeader (hWaveOut, &waveHdr, sizeof (WAVEHDR)) ; 
//播放静音符号waveOutWrite (hWaveOut, &waveHdr, sizeof (WAVEHDR)) ; 
//暂停waveOutPause(hWaveOut) ; 利用这段代码写一个win32程序,保证程序进程不会退出(可利用一个含有Sleep调用的死循环或弹出一个模态对话框实现),即可实现消除噪音的作用。 然而这样做仍然不够完善。我们希望系统在启动的时候,无论有用户登录与否,都能够自动地调用它。为了解决这一问题,我们应当把它改造为Windows的系统服务。 Windows系统服务的编写需要服从一定的格式规范,请参阅相关文献[3],本文不予详述。需要注意的是,如果编写为独立的Windows服务,仍然需要1,900K左右的内存;如果编写为寄存在svchost中的服务[4],则可以把内存占用量大大降低,达到300~400K。本文采用了后者。 完整代码如下(我们把服务名取作DenoiseSvc31): /*消电流噪声 svchost版 3.1*/ 
#include <windows.h> 
#include <stdio.h> 
 
#define SLEEP_TIME 10000 
#define SERVICE_NAME "DenoiseSvc31"//服务名 
#define MUTE_LENGTH 128 
#define SAMPLE_RATE 11025 
 
SERVICE_STATUS          ServiceStatus; 
SERVICE_STATUS_HANDLE   hStatus; 
 
void InitService(void) { 
    HWAVEOUT hWaveOut ; 
    BYTE mute[MUTE_LENGTH]; 
    WAVEFORMATEX waveformat = { 
        WAVE_FORMAT_PCM, 1, SAMPLE_RATE, SAMPLE_RATE, 1, 8, 0 
    }; 
    WAVEHDR waveHdr = { 
        0, MUTE_LENGTH, 0, 0, 0, 1, NULL, 0 
    }; 
 
    FillMemory(mute, MUTE_LENGTH, (BYTE)0x80); 
    waveHdr.lpData = mute; 
    waveOutOpen (&hWaveOut, WAVE_MAPPER, &waveformat, 0,0,CALLBACK_FUNCTION); 
    waveOutPrepareHeader (hWaveOut, &waveHdr, sizeof (WAVEHDR)) ; 
    waveOutWrite (hWaveOut, &waveHdr, sizeof (WAVEHDR)) ; 
    waveOutPause(hWaveOut) ; 
} 
 
void ControlHandler(DWORD request) 
{ 
    switch(request) { 
    case SERVICE_CONTROL_STOP: 
    case SERVICE_CONTROL_SHUTDOWN: 
        ServiceStatus.dwWin32ExitCode = 0; 
        ServiceStatus.dwCurrentState = SERVICE_STOPPED; 
        SetServiceStatus (hStatus, &ServiceStatus); 
        return; 
 
    default: 
        break; 
    } 
 
    // Report current status 
    SetServiceStatus (hStatus, &ServiceStatus); 
 
    return; 
} 
 
#pragma argsused 
__declspec(dllexport) VOID WINAPI ServiceMain(DWORD dwArgc, LPTSTR *lpszArgv) 
{ 
    ServiceStatus.dwServiceType = SERVICE_WIN32_SHARE_PROCESS; 
    ServiceStatus.dwCurrentState = SERVICE_START_PENDING; 
    ServiceStatus.dwControlsAccepted = SERVICE_ACCEPT_STOP | 
        SERVICE_ACCEPT_SHUTDOWN; 
    ServiceStatus.dwWin32ExitCode = 0; 
    ServiceStatus.dwServiceSpecificExitCode = 0; 
    ServiceStatus.dwCheckPoint = 0; 
    ServiceStatus.dwWaitHint = 0; 
 
    hStatus = RegisterServiceCtrlHandler( SERVICE_NAME, 
        (LPHANDLER_FUNCTION)ControlHandler); 
    if (hStatus == (SERVICE_STATUS_HANDLE)0) { 
        // Registering Control Handler failed 
        return; 
    } 
    // Initialize Service 
    InitService(); 
 
    // We report the running status to SCM. 
    ServiceStatus.dwCurrentState = SERVICE_RUNNING; 
    SetServiceStatus (hStatus, &ServiceStatus); 
 
    // The worker loop of a service 
    while (ServiceStatus.dwCurrentState == SERVICE_RUNNING) { 
        Sleep(SLEEP_TIME); 
    } 
    return; 
} Svchost服务要求可执行文件必须为动态链接库。我们把它编译为denoise.dll并拷贝到%windir%\system32目录下。剩下的任务就是把它安装到系统上。 为系统添加一个服务需要修改注册表。对于Svchost服务,需要修改的地方包括: l         HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Windows NT\CurrentVersion\SvcHost:把服务添加到某个Svchost组内。 l         HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Services:添加服务的主键及相关键值。 代码如下: Windows Registry Editor Version 5.00  [HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Services\DenoiseSvc31] "Type"=dword:00000020 "Start"=dword:00000002 "ErrorControl"=dword:00000001 "ImagePath"=hex(2):25,00,53,00,79,00,73,00,74,00,65,00,6d,00,52,00,6f,00,6f,00,\   74,00,25,00,5c,00,73,00,79,00,73,00,74,00,65,00,6d,00,33,00,32,00,5c,00,73,\   00,76,00,63,00,68,00,6f,00,73,00,74,00,2e,00,65,00,78,00,65,00,20,00,2d,00,\   6b,00,20,00,48,00,54,00,54,00,50,00,46,00,69,00,6c,00,74,00,65,00,72,00,00,\   00 "DisplayName"="DenoiseSvc31" "DependOnService"=hex(7):4c,00,61,00,6e,00,6d,00,61,00,6e,00,57,00,6f,00,72,00,\   6b,00,73,00,74,00,61,00,74,00,69,00,6f,00,6e,00,00,00,00,00 "DependOnGroup"=hex(7):00,00 "ObjectName"="NT AUTHORITY\\LocalService" "Description"="消除笔记本的高频电流噪音"  [HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Services\DenoiseSvc31\Enum] "0"="Root\\LEGACY_ALERTER\\0000" "Count"=dword:00000001 "NextInstance"=dword:00000001  [HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Services\DenoiseSvc31\Parameters] "AlertNames"=hex(7):00,00 "ServiceDll"=hex(2):25,00,53,00,79,00,73,00,74,00,65,00,6d,00,52,00,6f,00,6f,\   00,74,00,25,00,5c,00,53,00,79,00,73,00,74,00,65,00,6d,00,33,00,32,00,5c,00,\   64,00,65,00,6e,00,6f,00,69,00,73,00,65,00,2e,00,64,00,6c,00,6c,00,00,00  [HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Services\DenoiseSvc31\Security] "Security"=hex:01,00,14,80,90,00,00,00,9c,00,00,00,14,00,00,00,30,00,00,00,02,\   00,1c,00,01,00,00,00,02,80,14,00,ff,01,0f,00,01,01,00,00,00,00,00,01,00,00,\   00,00,02,00,60,00,04,00,00,00,00,00,14,00,fd,01,02,00,01,01,00,00,00,00,00,\   05,12,00,00,00,00,00,18,00,ff,01,0f,00,01,02,00,00,00,00,00,05,20,00,00,00,\   20,02,00,00,00,00,14,00,8d,01,02,00,01,01,00,00,00,00,00,05,0b,00,00,00,00,\   00,18,00,fd,01,02,00,01,02,00,00,00,00,00,05,20,00,00,00,23,02,00,00,01,01,\   00,00,00,00,00,05,12,00,00,00,01,01,00,00,00,00,00,05,12,00,00,00  [HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Windows NT\CurrentVersion\SvcHost] "HTTPFilter"=hex(7):48,00,54,00,54,00,50,00,46,00,69,00,6c,00,74,00,65,00,72,\   00,00,00,44,00,65,00,6e,00,6f,00,69,00,73,00,65,00,53,00,76,00,63,00,33,00,\   31,00,00,00,00,00 把它保存在denoise.reg中双击运行,然后重启机器,噪音问题就解决了。 性能与不足 经过测试,该服务占用的内存约为370K,基本不占用CPU,对系统的负担是很小的。它消除噪音彻底,无论是否使用电池,以及系统是否从休眠中恢复,都不会再度产生噪音。 在运行该服务之后,少数情况下操作系统的事件配音的质量会受到影响,比如关机音乐会发生轻微爆音。但是对音乐播放器未造成能观察到的影响。 参考文献 [1] IBM ThinkPad R52, T43 BIOS update. [2] Dell技术支持网站给出的消除噪音解决方案 [3] Five Steps to Writing Windows Services in C [4] 创建SvcHost.exe调用的服务原理与实践 |