Для того чтобы установить соединение с Internet в Windows Mobile предусмотрен специальный программный интерфейс – Connection Manager API.
Пользоваться им довольно просто. И вот пример такого использования для C# и C++ приведен ниже:
C# + .NET Compact Framework
using System;
using System.Collections;
using System.Collections.Generic;
using System.Runtime.InteropServices;
using System.Threading;
using System.Reflection;
namespace GPRSConnection
{
public class GPRSConnection
{
const int S_OK = 0;
const uint CONNMGR_PARAM_GUIDDESTNET = 0x1;
const uint CONNMGR_FLAG_PROXY_HTTP = 0x1;
const uint CONNMGR_PRIORITY_USERINTERACTIVE = 0x08000;
const uint INFINITE = 0xffffffff;
const uint CONNMGR_STATUS_CONNECTED = 0x10;
static Hashtable ht = new Hashtable();
static GPRSConnection()
{
ManualResetEvent mre = new ManualResetEvent(false);
mre.Handle = ConnMgrApiReadyEvent();
mre.WaitOne();
CloseHandle(mre.Handle);
}
~GPRSConnection()
{
ReleaseAll();
}
public static bool Setup(Uri url)
{
return Setup(url.ToString());
}
public static bool Setup(string urlStr)
{
ConnectionInfo ci = new ConnectionInfo();
IntPtr phConnection = IntPtr.Zero;
uint status = 0;
if (ht[urlStr] != null)
return true;
if (ConnMgrMapURL(urlStr, ref ci.guidDestNet, IntPtr.Zero) != S_OK)
return false;
ci.cbSize = (uint)Marshal.SizeOf(ci);
ci.dwParams = CONNMGR_PARAM_GUIDDESTNET;
ci.dwFlags = CONNMGR_FLAG_PROXY_HTTP;
ci.dwPriority = CONNMGR_PRIORITY_USERINTERACTIVE;
ci.bExclusive = 0;
ci.bDisabled = 0;
ci.hWnd = IntPtr.Zero;
ci.uMsg = 0;
ci.lParam = 0;
if (ConnMgrEstablishConnectionSync(ref ci, ref phConnection, INFINITE, ref status) != S_OK &&
status != CONNMGR_STATUS_CONNECTED)
return false;
ht[urlStr] = phConnection;
return true;
}
public static bool Release(Uri url)
{
return Release(url.ToString());
}
public static bool Release(string urlStr)
{
return Release(urlStr, true);
}
private static bool Release(string urlStr, bool removeNode)
{
bool res = true;
IntPtr ph = IntPtr.Zero;
if (ht[urlStr] == null)
return true;
ph = (IntPtr)ht[urlStr];
if (ConnMgrReleaseConnection(ph, 1) != S_OK)
res = false;
CloseHandle(ph);
if (removeNode)
ht.Remove(urlStr);
return res;
}
public static void ReleaseAll()
{
foreach (DictionaryEntry de in ht)
{
Release((string)de.Key, false);
}
ht.Clear();
}
[StructLayout(LayoutKind.Sequential)]
public struct ConnectionInfo
{
public uint cbSize;
public uint dwParams;
public uint dwFlags;
public uint dwPriority;
public int bExclusive;
public int bDisabled;
public Guid guidDestNet;
public IntPtr hWnd;
public uint uMsg;
public uint lParam;
public uint ulMaxCost;
public uint ulMinRcvBw;
public uint ulMaxConnLatency;
}
[DllImport("cellcore.dll")]
private static extern int ConnMgrMapURL(string pwszURL, ref Guid pguid, IntPtr pdwIndex);
[DllImport("cellcore.dll")]
private static extern int ConnMgrEstablishConnectionSync(ref ConnectionInfo ci, ref IntPtr phConnection, uint dwTimeout, ref uint pdwStatus);
[DllImport("cellcore.dll")]
private static extern IntPtr ConnMgrApiReadyEvent();
[DllImport("cellcore.dll")]
private static extern int ConnMgrReleaseConnection(IntPtr hConnection, int bCache);
[DllImport("coredll.dll")]
private static extern int CloseHandle(IntPtr hObject);
}
}
Пример использования
public void DoTcpConnection()
{
string t = System.IO.Path.AltDirectorySeparatorChar.ToString() + System.IO.Path.DirectorySeparatorChar.ToString();
string url = "www.msn.com";
bool res = GPRSConnection.Setup(Uri.UriSchemeHttp +
Uri.SchemeDelimiter + url + Path.AltDirectorySeparatorChar);
if (res)
{
TcpClient tc = new TcpClient(url, 80);
NetworkStream ns = tc.GetStream();
byte[] buf = new byte[100];
ns.Write(buf, 0, 100);
tc.Client.Shutdown(SocketShutdown.Both);
ns.Close();
tc.Close();
MessageBox.Show("Wrote 100 bytes");
}
else
{
MessageBox.Show("Connection establishment failed");
}
}
C++
Singleton.h
#ifndef _SINGLETON_H
#define _SINGLETON_H
template<typename T> class Singleton
{
public:
static T & Instance()
{
static T instance;
return instance;
}
};
#endif
GPRSConnection.h
#pragma once
#include <windows.h>
#include <connmgr.h>
#include <map>
#include "Singleton.h"
class GPRSConnection : public Singleton<GPRSConnection>
{
friend class Singleton<GPRSConnection>;
#ifndef _UNICODE
typedef std::string StringType;
#else
typedef std::wstring StringType;
#endif
bool apiReady;
std::map<StringType, HANDLE> Connections;
protected:
GPRSConnection() : apiReady(false)
{
do
{
HANDLE apiHandle = ConnMgrApiReadyEvent();
if(!apiHandle) break;
if(WaitForSingleObject(apiHandle, 10000) != WAIT_OBJECT_0) break;
CloseHandle(apiHandle);
apiReady = true;
}
while(false);
}
public:
~GPRSConnection()
{
ReleaseAll();
}
bool Setup(LPCTSTR url)
{
StringType urlInternal = url;
if(Connections[urlInternal] != NULL) return true;
CONNMGR_CONNECTIONINFO ci;
if(ConnMgrMapURL(url, &ci.guidDestNet, NULL) != S_OK) return false;
ci.cbSize = sizeof(CONNMGR_CONNECTIONINFO);
ci.dwParams = CONNMGR_PARAM_GUIDDESTNET;
ci.dwFlags = CONNMGR_FLAG_PROXY_HTTP;
ci.dwPriority = CONNMGR_PRIORITY_USERINTERACTIVE;
ci.bExclusive = 0;
ci.bDisabled = 0;
ci.hWnd = NULL;
ci.uMsg = 0;
DWORD status = CONNMGR_STATUS_UNKNOWN;
HANDLE phConnection;
if (ConnMgrEstablishConnectionSync(&ci, &phConnection, -1, &status) != S_OK &&
status != CONNMGR_STATUS_CONNECTED) return false;
Connections[urlInternal] = phConnection;
return true;
}
bool Release(LPCTSTR url, bool removeNode)
{
StringType urlInternal = url;
bool res = true;
if(Connections[urlInternal] == NULL) return true;
if (ConnMgrReleaseConnection(Connections[urlInternal], 1) != S_OK) res = false;
CloseHandle(Connections[urlInternal]);
if(removeNode)
{
Connections.erase(urlInternal);
}
else
{
Connections[urlInternal] = NULL;
}
return res;
}
void ReleaseAll()
{
for(std::map<StringType, HANDLE>::iterator i = Connections.begin(); i != Connections.end(); ++i)
{
Release(i->first.c_str(), false);
}
Connections.clear();
}
};
Пример использования
void MainFrame::OnCONNECTClick( wxCommandEvent& event )
{
TransferDataFromWindow();
bool res = GPRSConnection::Instance().Setup(m_URL.GetData());
if(res)
{
wxLogMessage(_("Connection established"));
// Дальше здесь можно делать всякие штуки
}
else
{
wxLogMessage(_("Connection error"));
}
}
Скачать исходный код к статье (C++/C#)
Вообще-то в платформе .Net Можно писать и на C++ и на еще целом ряде языков в том и фишка платформы. Идея платформы – использование промежуточного универсального байт-кода. Не зависимого от процессора и высокоуровнего языка, при этом можно подключать даже модули написанные на разных языках.
http://ru.wikipedia.org/wiki/Microsoft_.NET
У Вас получилось написать приложение для Windows Mobile на Managed C++ и .NET CF? Хотел бы я на это посмотреть. Managed C++ не поддерживается для Smart Device проектов.
А банальные обертки к unmanaged-библиотекам это совсем не то что хотелось бы.