首页
社区
课程
招聘
[分享]WinCE5.0 RAS Reg Set
发表于: 2009-9-17 10:17 6693

[分享]WinCE5.0 RAS Reg Set

2009-9-17 10:17
6693

網路上已有許多前輩 Post 過相關文章, 不過和自己做的部份有些出入, 但小弟我有 Try 過我的 Code 是可以 Work 的.

(1) WinCE 下的 RAS 的 Modem Parameter 是 Binary Data, 此 Binary Data Structure 在 M$DN 上似乎找不到正式文件, 得笨笨的一個一個猜.
(2) Device Name 和 Entry Name 不可混淆, 之前就是這部份混淆了,  之後還是靠比對 寫入 & Dialog 產生 的 Binary Data 才知道問提出在這.
(3) Modem 似乎不能在 OS Boot 之後才建立 (會找不到, 猜想可能是 Boot 時就讀取 Modem Reg Variable), 所以一定要 Build OS 前先建一個 Modem 才可以, 建立 Modem 比較簡單的方式則是先在 Reg 中沒有 Modem 的 OS Boot 後手動建立一個 Modem, 再用 Remote Reg (eVC中有) View And 記錄下來, 然後手動加進 Reg, ReBuild OS.
(4) 可以做到 AutoDial, 而且這樣比較好掌控 (否則如果是程式 A 說要連上網, 那麼誰要負責幫它 Dial Up), 不過 AutoDial 的 UI 在 OS 中, 要客製化比較麻煩, 要在 Ap Layer 中客製化 UI 的方式還沒研究.

RASRegSet 是以 Export Entire Class 的 DLL 方式 Implement, 主要的檔案有 3 個, Macro.h, CRASRegSet.h CRASRegSet.cpp, 分別 List 如下 (For WinCE 5.0) :
Macro.h (For Export Entire Class PreDefine)

#ifndef __RAS_MACRO__
#define __RAS_MACRO__

#ifndef AFX_EXT_DATA
#ifdef _AFXEXT
#define AFX_EXT_CLASS AFX_CLASS_EXPORT
#define AFX_EXT_API AFX_API_EXPORT
#define AFX_EXT_DATA AFX_DATA_EXPORT
#define AFX_EXT_DATADEF
#else
#define AFX_EXT_CLASS AFX_CLASS_IMPORT
#define AFX_EXT_API AFX_API_IMPORT
#define AFX_EXT_DATA AFX_DATA_IMPORT
#define AFX_EXT_DATADEF
#endif
#endif

#endif

CRASRegSet.h

// CRASRegSet.h: interface for the CRASRegSet class.
//
//////////////////////////////////////////////////////////////////////

#if !defined(AFX_CRASREGSET_H__96AA9E65_FEE2_441F_A7E2_57CEF87FA627__INCLUDED_)
#define AFX_CRASREGSET_H__96AA9E65_FEE2_441F_A7E2_57CEF87FA627__INCLUDED_

#if _MSC_VER > 1000
#pragma once
#endif // _MSC_VER > 1000

#include "Macro.h"
#include
#include

#define __REG_NAME__ _T("BT Connection")
#define __DEVICE_NAME__ _T("Bluetooth DUN on COM2")
#define __PHONE_NUMBER__ _T("\*99\#")
#define __COUNTRY_CODE__ 0×376
#define __AREA_CODE__ _T("03")
#define __AT_CMD_LEN__ 331

// Following Data Struct Is Reversing From HKEY_CURRENT_USER\Comm\RasBook\Xxxx, (Xxxx Is Modem Device Name)
// Use For API RasSetEntryProperties Parameter, For Set Modem & Extra Command Like "+cgdcont=1,"ip","internet"
// 2008/10/03, Tony.Jou

typedef struct {

WORD wHeader; // 0×00(L:2), Val = 0×30, Unknown

WORD wWaitForCreditCardSec; // 0×02(L:2), Val = 0×0, Wait For Credit Card Tone Seconds,

WORD wCancelTimeOut; // 0×04(L:2), Val = 78 00 -> 0×78

WORD wReserved1; // 0×06(L:2), Val = 0×0,

BYTE bFlowControl; // 0×08(L:1), Val = 0×0,
// F.C. = None, Val = 0×0,
// F.C. = H.W., Val = 0×10,
// F.C. = S.W., Val = 0×20,

BYTE bWaitForDialTone; // 0×09(L:1), Val = 0×1, Wait For Dial Tone Before Dialing
// Enable Wait For Dial Tone Before Dialing, Val = 0×1
// Disable Wait For Dial Tone Before Dialing, Val = 0×3

WORD wReserved2; // 0×0A(L:2), Val = 0×0,

UINT uBaudRate; // 0×0C(L:4), Val = 00 c2 01 00, 0×0001c200 = 115200

WORD wTerminal; // 0×10(L:2), Val = 00(L^) 00(H) -> 0×0, digital (d2)(d1)(d0),
// d2:Manual Dial,
// d1:Use terminal window before dialing,
// d0:Use terminal window after dialing,

BYTE bDataBits; // 0×12(L:1), Val = 0×8,

BYTE bStopBits; // 0×13(L:1), Val = 0×0,
// StopBits = 1, Val = 0×0
// StopBits = 1.5,Val = 0×1
// StopBits = 2, Val = 0×2

WORD wParity; // 0×14(L:2), Val = 00(^L) 00(H) -> 0×0
// Parity = None, Val = 0×0
// Parity = Odd, Val = 0×1
// Parity = Even, Val = 0×2
// Parity = Mark, Val = 0×3
// Parity = Space,Val = 0×4

WCHAR wszAtCmd[__AT_CMD_LEN__]; // 0×16(L:662),
// __AT_CMD_LEN__ ->331, Why "331" -> Reg DevCfg TotalLen : 684(0~0×2AB)
// 684(0~0×2AB) – 22(0×0~0×15->0×16) = 662(0×16~0×2AB->0×296)
// 662(0×16~0×2AB->0×296) / sizeof(WCHAR)
} sDevConfig;

class AFX_EXT_CLASS CRASRegSet
{
public:
CRASRegSet();
virtual ~CRASRegSet();
bool UpdateRASReg();

private:
sDevConfig m_DevConfig;
RASENTRY m_RASEntry;
bool InitVar();
bool GetRASEntries();
bool GetDeficeID(TCHAR *btname, int *iDeviceID);
};

#endif // !defined(AFX_CRASREGSET_H__96AA9E65_FEE2_441F_A7E2_57CEF87FA627__INCLUDED_)

CRASRegSet.cpp

// CRASRegSet.cpp: implementation of the CRASRegSet class.
//
//////////////////////////////////////////////////////////////////////

#include "stdafx.h"
#include "CRASRegSet.h"

#ifdef _DEBUG
#undef THIS_FILE
static char THIS_FILE[]=__FILE__;
#define new DEBUG_NEW
#endif

//////////////////////////////////////////////////////////////////////
// Construction/Destruction
//////////////////////////////////////////////////////////////////////

CRASRegSet::CRASRegSet()
{
memset(m_DevConfig.wszAtCmd,0,__AT_CMD_LEN__*sizeof(WCHAR));
}

CRASRegSet::~CRASRegSet()
{

}

bool CRASRegSet::UpdateRASReg()
{
DWORD dwRet = 0;
bool bRet = false;
DWORD dwBufferSize = 0;
DWORD dwSize = 0;

int iLineID = 0;
int iDeviceID = 0;

LONG lRet = -1;

// This is important! Find the buffer size (different from sizeof(RASENTRY)).
RasGetEntryProperties(NULL, L"", NULL, &dwBufferSize, NULL, NULL);
dwSize = sizeof(m_DevConfig);

bRet = InitVar();
//bRet = true;

if (bRet) {

dwRet = RasSetEntryProperties(
NULL,
__REG_NAME__,
&m_RASEntry,
dwBufferSize,
(LPBYTE)&m_DevConfig,
dwSize
);

switch (dwRet) {
case ERROR_BUFFER_INVALID:
MessageBox(NULL,_T("ERROR_BUFFER_INVALID"),NULL,MB_OK);
break;
case ERROR_CANNOT_OPEN_PHONEBOOK:
MessageBox(NULL,_T("ERROR_CANNOT_OPEN_PHONEBOOK"),NULL,MB_OK);
break;
default:
break;
}

bRet = (dwRet?false:true);

dwBufferSize = 0;

m_RASEntry.dwSize = sizeof(RASENTRY);

RasGetEntryProperties(NULL, __REG_NAME__, NULL, &dwBufferSize, NULL, NULL);

dwRet = RasGetEntryProperties(
NULL,
__REG_NAME__,
&m_RASEntry,
&dwBufferSize,
(LPBYTE)&m_DevConfig,
&dwSize
);
bRet = (dwRet?false:true);
}

if (bRet) {
bRet = GetRASEntries();
}

if (bRet) {
bRet = GetDeficeID(L"Bluetooth", &iDeviceID);
}

return bRet;

if (bRet) {

//lRet = lineSetDevConfig((DWORD)iDeviceID, &m_DevConfig, dwSize, L"Comm");
//lRet = lineSetDevConfig((DWORD)iDeviceID, &m_DevConfig, dwSize, L"tapi/line");
// lRet = lineSetDevConfig((DWORD)iDeviceID, &m_DevConfig, dwSize, L"comm/datamodem/portname/Bluetooth DUN on COM2\0");
//lRet = lineSetDevConfig((DWORD)iDeviceID, &m_DevConfig, dwSize, L"Comm/datamodem");

bRet = (lRet?false:true);
}

return bRet;
}

bool CRASRegSet::InitVar()
{
// Read Config …

// m_RASEntry Variable
DWORD dwFlagOptions = 0;
DWORD dwChannel = 0;
bool bSpecificDNS = false;
bool bSpecificIpAddr = false;
int iDeviceType = 0;

// Set Variable

m_RASEntry.dwSize = sizeof(RASENTRY);

memset((void*)&m_RASEntry, 0, m_RASEntry.dwSize);

m_RASEntry.dwfOptions = RASEO_ProhibitEAP;

dwFlagOptions = RASEO_RemoteDefaultGateway;

if (bSpecificDNS) {
dwFlagOptions |= RASEO_SpecificNameServers;
// example : 168.95.1.1 -> 0xA8, 0×5F, 0×1, 0×1
m_RASEntry.ipaddrDns.a = 0×1;
m_RASEntry.ipaddrDns.b = 0×1;
m_RASEntry.ipaddrDns.c = 0×5F;
m_RASEntry.ipaddrDns.d = 0xA8;

// example : 168.95.1.2 -> 0xA8, 0×5F, 0×1, 0×2
m_RASEntry.ipaddrDnsAlt.a = 0×2;
m_RASEntry.ipaddrDnsAlt.b = 0×1;
m_RASEntry.ipaddrDnsAlt.c = 0×5F;
m_RASEntry.ipaddrDnsAlt.d = 0xA8;

// example : 168.95.1.3 -> 0xA8, 0×5F, 0×1, 0×3
m_RASEntry.ipaddrWins.a = 0×3;
m_RASEntry.ipaddrWins.b = 0×1;
m_RASEntry.ipaddrWins.c = 0×5F;
m_RASEntry.ipaddrWins.d = 0xA8;

// example : 168.95.1.4 -> 0xA8, 0×5F, 0×1, 0×4
m_RASEntry.ipaddrWinsAlt.a = 0×4;
m_RASEntry.ipaddrWinsAlt.b = 0×1;
m_RASEntry.ipaddrWinsAlt.c = 0×5F;
m_RASEntry.ipaddrWinsAlt.d = 0xA8;
}

if (bSpecificIpAddr) {
dwFlagOptions |= RASEO_SpecificIpAddr;
// example : 203.22.95.42 -> 0xCB, 0×16, 0×5F, 0×2A
m_RASEntry.ipaddr.a = 0×2A;
m_RASEntry.ipaddr.b = 0×5F;
m_RASEntry.ipaddr.c = 0×16;
m_RASEntry.ipaddr.d = 0xCB;
}

m_RASEntry.dwfOptions = dwFlagOptions;

m_RASEntry.dwCountryCode = __COUNTRY_CODE__; //

_tcscpy(m_RASEntry.szAreaCode, __AREA_CODE__);

_tcscpy(m_RASEntry.szLocalPhoneNumber, __PHONE_NUMBER__);

_tcscpy(m_RASEntry.szDeviceName, __DEVICE_NAME__);

_tcscpy(m_RASEntry.szX25PadType, _T(""));
_tcscpy(m_RASEntry.szX25Address, _T(""));
_tcscpy(m_RASEntry.szX25Facilities, _T(""));
_tcscpy(m_RASEntry.szX25UserData, _T(""));

m_RASEntry.dwfNetProtocols = RASNP_Ip;
m_RASEntry.dwFramingProtocol = RASFP_Ppp;

switch (iDeviceType) {
case 0:
_tcscpy (m_RASEntry.szDeviceType, RASDT_Modem);
break;
case 1:
_tcscpy (m_RASEntry.szDeviceType, RASDT_Direct);
break;
case 2:
_tcscpy (m_RASEntry.szDeviceType, RASDT_Modem);
break;
default:
_tcscpy (m_RASEntry.szDeviceType, RASDT_Vpn);
break;
}

// Number specifying the number of channels supported by the device,
// where 1 is mono, 2 is stereo, and so on.
m_RASEntry.dwChannels = dwChannel;
m_RASEntry.dwReserved1 = 0;
m_RASEntry.dwReserved2 = 0;
m_RASEntry.dwCustomAuthKey = 0;

// Init DevConfig
/*
WORD wHeader; // 0×00(L:2), Val = 0×30, Unknown

WORD wWaitForCreditCardSec; // 0×02(L:2), Val = 0×0, Wait For Credit Card Tone Seconds,

WORD wCancelTimeOut; // 0×04(L:2), Val = 78 00 -> 0×78

WORD wReserved1; // 0×06(L:2), Val = 0×0,

BYTE bFlowControl; // 0×08(L:1), Val = 0×0,
// F.C. = None, Val = 0×0,
// F.C. = H.W., Val = 0×10,
// F.C. = S.W., Val = 0×20,

BYTE bWaitForDialTone; // 0×09(L:1), Val = 0×1, Wait For Dial Tone Before Dialing
// Enable Wait For Dial Tone Before Dialing, Val = 0×1
// Disable Wait For Dial Tone Before Dialing, Val = 0×3

WORD wReserved2; // 0×0A(L:2), Val = 0×0,

UINT uBaudRate; // 0×0C(L:4), Val = 00 c2 01 00, 0×0001c200 = 115200

WORD wTerminal; // 0×10(L:2), Val = 00(L^) 00(H) -> 0×0, digital (d2)(d1)(d0),
// d2:Manual Dial,
// d1:Use terminal window before dialing,
// d0:Use terminal window after dialing,

BYTE bDataBits; // 0×12(L:1), Val = 0×8,

BYTE bStopBits; // 0×13(L:1), Val = 0×0,
// StopBits = 1, Val = 0×0
// StopBits = 1.5,Val = 0×1
// StopBits = 2, Val = 0×2

WORD wParity; // 0×14(L:2), Val = 00(^L) 00(H) -> 0×0
// Parity = None, Val = 0×0
// Parity = Odd, Val = 0×1
// Parity = Even, Val = 0×2
// Parity = Mark, Val = 0×3
// Parity = Space,Val = 0×4

WCHAR wszAtCmd[331]; // 0×16(L:662),
// Why "331" -> Reg DevCfg TotalLen : 684(0~0×2AB)
// 684(0~0×2AB) – 22(0×0~0×15->0×16) = 662(0×16~0×2AB->0×296)
// 662(0×16~0×2AB->0×296) / sizeof(WCHAR)
*/
m_DevConfig.wHeader = 0×30; // 0×00(L:2)
m_DevConfig.wWaitForCreditCardSec = 0×0;// 0×02(L:2),
m_DevConfig.wCancelTimeOut = 0×78; // 0×04(L:2),
m_DevConfig.wReserved1 = 0×0; // 0×06(L:2),
m_DevConfig.bFlowControl = 0×0; // 0×08(L:1),
m_DevConfig.bWaitForDialTone = 0×1; // 0×09(L:1),
m_DevConfig.wReserved2 = 0×0; // 0×0A(L:2),
m_DevConfig.uBaudRate = 0×0001c200; // 0×0C(L:4),
m_DevConfig.wTerminal = 0×0; // 0×10(L:2),
m_DevConfig.bDataBits = 0×8; // 0×12(L:1),
m_DevConfig.bStopBits = 0×0; // 0×13(L:1),
m_DevConfig.wParity = 0×0; // 0×14(L:2),
_tcscpy(m_DevConfig.wszAtCmd, _T("+cops=1,2,\"46692\";+cgdcont=1,\"ip\",\"internet\""));
return true;
}

bool CRASRegSet::GetRASEntries()
{
DWORD dwRet = -1;
DWORD cb;
DWORD cEntries;
bool bRet = false;
LPRASENTRYNAME lpRASEntryName;
int i = 0;

lpRASEntryName = (LPRASENTRYNAME)LocalAlloc(LPTR, sizeof(RASENTRYNAME));
lpRASEntryName->dwSize = sizeof(RASENTRYNAME);
if ((dwRet = RasEnumEntries(NULL, NULL, lpRASEntryName, &cb, &cEntries))
== ERROR_BUFFER_TOO_SMALL)
{
lpRASEntryName = (LPRASENTRYNAME)LocalAlloc(LPTR, cb);
lpRASEntryName->dwSize = sizeof(RASENTRYNAME);
}

// Calling RasEnumEntries to enumerate the phonebook entries
dwRet = RasEnumEntries(NULL, NULL, lpRASEntryName, &cb, &cEntries);

if (dwRet != ERROR_SUCCESS)
{
TRACE(_T("RasEnumEntries failed: Error %d\n"), dwRet);
}
else
{
TRACE(_T("Phone book entries in the default phonebook:\n\n"));
for(i=0;i < cEntries;i++)
{
TRACE(_T("%s\n"),lpRASEntryName->szEntryName);
if(_tcsncmp((lpRASEntryName + i)->szEntryName, __DEVICE_NAME__, _tcslen(__DEVICE_NAME__)) == 0)
{
lpRASEntryName = (LPRASENTRYNAME)LocalAlloc(LPTR, cb);
lpRASEntryName->dwSize = sizeof(RASENTRYNAME);
return TRUE;
}
}
}

bRet = (dwRet?false:true);

return bRet;
}

bool CRASRegSet::GetDeficeID(TCHAR *btname, int *iDeviceID)
{
LPRASDEVINFO lpRasDevInfo = NULL;
DWORD dwBufSize = 0;
DWORD dwNumDevices = 0;
DWORD dwDeviceID = 0;
DWORD dwErr;

// find the buffer size needed
dwErr = RasEnumDevices(NULL, &dwBufSize, &dwNumDevices);
if (!dwBufSize) return false;

lpRasDevInfo = (LPRASDEVINFO)LocalAlloc(LPTR, dwBufSize);

if (!lpRasDevInfo) return false;

lpRasDevInfo->dwSize = sizeof(RASDEVINFO);

if (RasEnumDevices(lpRasDevInfo, &dwBufSize, &dwNumDevices))
{
LocalFree(lpRasDevInfo);
return false;
}

dwDeviceID = 0;
//
// Find the correct device ID for this connection type
//
while (dwDeviceID < dwNumDevices)
{
if (wcsncmp((lpRasDevInfo + dwDeviceID)->szDeviceType, RASDT_Modem, wcslen(RASDT_Modem)) == 0)
{
if(wcsncmp((lpRasDevInfo + dwDeviceID)->szDeviceName, btname, wcslen(btname)) == 0)
{
LocalFree(lpRasDevInfo);
*iDeviceID = dwDeviceID;
return true;
}
}
dwDeviceID++;
}
LocalFree(lpRasDevInfo);
return false;
}

APN 若不清楚的話可以 Ref 一下 :
0a2K9s2c8@1M7q4)9K6b7g2)9J5c8W2)9J5c8Y4N6%4N6#2)9J5k6i4c8S2L8X3W2%4K9r3q4Q4x3X3g2G2M7X3N6Q4x3X3g2#2K9#2)9J5c8X3N6H3M7Y4y4Q4x3X3g2Z5N6r3#2D9
是 Free 的, Taiwan 部份 Data 都是正確的, 其他區域不知道正確否.

附件即是版上所貼的 Source Code, eVC 版的.


[培训]内核驱动高级班,冲击BAT一流互联网大厂工作,每周日13:00-18:00直播授课

上传的附件:
收藏
免费 7
支持
分享
最新回复 (0)
游客
登录 | 注册 方可回帖
返回