Introduction
Dialing parameters/patterns are strings of information that govern how a phone number is dialed when establishing a RAS connection in Pocket PC. For example:
- 9,G would dial a 9 and then the base phone number.
- 1FG would dial 1, the area code, and then the phone number.
Unfortunately, there is no documented API for modifying the dialing parameters in Pocket PC. All of the dialing parameters/patterns are stored in the registry. Being confronted with this problem several times before and finding very little information on the topic, I decided to write a short article on how to do change these settings with EVC 3.0. Writing the DLL in unmanaged code allows for the DLL to be used in EVB
(Which I would not recommend anyone to use), EVC, and with the .NET Languages using P/Invoke.
The code in this project will explain how to each of the fields in the screenshots above.
Using the code
Now, modifying the device registry is not that difficult, but the type/format in which the settings are stored makes it less than obvious as to what needs to be done to modify these settings. To save you the heartache of figuring this out, I have done the dirty work for you. Notice the screenshot from the device registry below:
HKEY_CURRENT_USER\ControlPanel\Dial\Locations
This is all fine and dandy, you might say, but where are the settings for Country Code, Tone/Pulse dialing, and the Disable Call Waiting Dial String?
After asking myself this question, I did a little google research and found that the registry actually stores the values in the following format:
- Location
- Local Calls Dial String
- Long Distance Calls Dial String
- International Calls Dial String
- Area Codes Dial String
- Country Code
- Disable Call Waiting Dial String
- Tone or Pulse, where Tone = 0 and Pulse = 1
It turns out that the registry editor has a difficult time displaying registry keys of the type
REG_MULTI_SZ
. According to the Pocket PC 2002 SDK Documentation
REG_MULTI_SZ
is an array of null-terminated strings, terminated by two null characters. So, somehow the registry editor is getting a little confused when displaying this array of strings, and with that you are whisked away on a wild goose chase to find where the rest of the settings are stored only to determine a few days later that they where right in front of you all along.
Now that we know where all the settings are REALLY stored, we can begin coding.
BOOL WINAPI SetDialingParameters(WCHAR *KeyName,
WCHAR *Location,
WCHAR *LocalCalls,
WCHAR *LongDistanceCalls,
WCHAR *InternationalCalls,
WCHAR *AreaCode,
WCHAR *DisableCallWaitingSequence,
WCHAR *CountryCode,
WCHAR *ToneOrPulse
)
{
HKEY hKey;
DWORD dataType = REG_MULTI_SZ;
LONG retVal = 0;
LONG ConfigurationStringSize = 512;
WCHAR *ConfigurationString = new WCHAR[ConfigurationStringSize];
memset(ConfigurationString,'\0',512);
wcscat(ConfigurationString, Location);
wcscat(ConfigurationString, TEXT("$"));
wcscat(ConfigurationString, LocalCalls);
wcscat(ConfigurationString, TEXT("$"));
wcscat(ConfigurationString, LongDistanceCalls);
wcscat(ConfigurationString, TEXT("$"));
wcscat(ConfigurationString, InternationalCalls);
wcscat(ConfigurationString, TEXT("$"));
wcscat(ConfigurationString, AreaCode);
wcscat(ConfigurationString, TEXT("$"));
wcscat(ConfigurationString, DisableCallWaitingSequence);
wcscat(ConfigurationString, TEXT("$"));
wcscat(ConfigurationString, CountryCode);
wcscat(ConfigurationString, TEXT("$"));
wcscat(ConfigurationString, ToneOrPulse);
wcscat(ConfigurationString, TEXT("$"));
int ConfigStringLen = wcslen(ConfigurationString);
for(int x = 0; x < ConfigStringLen; ++x)
{
if(ConfigurationString[x] == '$')
ConfigurationString[x] = '\0';
}
retVal = RegOpenKeyEx(HKEY_CURRENT_USER ,
TEXT("ControlPanel\\Dial\\Locations"),
0, KEY_READ, &hKey);
if(retVal != ERROR_SUCCESS)
{
delete [] ConfigurationString;
return false;
}
retVal = RegSetValueEx(hKey, KeyName, NULL, dataType,
(PBYTE)ConfigurationString,
ConfigurationStringSize);
RegCloseKey(hKey);
delete [] ConfigurationString;
if(retVal != ERROR_SUCCESS)
return false;
else
return true;
}
That's all the code it takes to store the key! Of course now we would want to put this inside a DLL so we can call it from our application. Refer to source file at the top of this article for details on this.
After creating the DLL, you will want to put it to good use. We will now walk through P/Invoking the DLL from managed code since that is what most of you guys will probably be using this with.
Fire up Visual Studio .NET 2003 and create a new Smart Device Application for Pocket PC.
Create a new class for your P/Invoke method and insert the code below into your class definition:
[System.Runtime.InteropServices.DllImport("DialingParameters.dll")]
public static extern int SetDialingParameters(string KeyName,
string Location,
string LocalCalls,
string LongDistanceCalls,
string InternationalCalls,
string AreaCode,
string DisableCallWaitingSequence,
string CountryCode,
string ToneOrPulse
);
That's it! To call this DLL from EVB, you would need to make a declare statement at the top of your form much like the following:
Declare Function RasDial Lib "DialingParameters.dll"
Alias "SetDialingParameters" (ByVal KeyName As String,
ByVal Location As String,
ByVal LocalCalls As String,
ByVal LongDistanceCalls As String,
ByVal InternationalCalls As String,
ByVal AreaCode As String,
ByVal DisableCallWaitingSequence As String,
ByVal CountryCode As String,
ByVal ToneOrPulse As String
) As Long
Points of Interest
Remember to keep your EVC DLL in the same folder as your consuming application or your method call will fail.