/* e * Copyright (C) 2010 Marc A. Paradise * * This program is free software; you can redistribute it and/or * modify it under the terms of the GNU General Public License * as published by the Free Software Foundation; either version 2 * of the License, or (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */ package org.bbssh.net; import java.io.IOException; import javax.microedition.io.Connector; import javax.microedition.io.HttpConnection; import net.rim.device.api.applicationcontrol.ApplicationPermissions; import net.rim.device.api.servicebook.ServiceBook; import net.rim.device.api.servicebook.ServiceRecord; import net.rim.device.api.system.RadioInfo; import net.rim.device.api.system.WLANInfo; import org.bbssh.model.Settings; import org.bbssh.model.SettingsManager; // @todo this must be version specific, to allow usage of the new connection tools in 5.0 and 6.0 ; also // retry properly upon failure. public class ConnectionHelper { public static final byte CONNECTION_TYPE_TCP = 0; public static final byte CONNECTION_TYPE_BES = 1; public static final byte CONNECTION_TYPE_WIFI = 2; public static final byte CONNECTION_TYPE_WAP2 = 3; public static final byte CONNECTION_TYPE_MDS_PUBLIC = 4; public static final byte CONNECTION_TYPE_AUTO = 5; public static final byte CONNECTION_TYPE_COUNT = 5; public static final byte PROXY_MODE_NONE = 0; public static final byte PROXY_MODE_PERSISTENT = 1; public static final byte PROXY_MODE_TRANSIENT = 1; public static HttpConnection getHttpConnection(byte connType, String URL) throws IOException { HttpConnection c = null; StringBuffer conn = new StringBuffer(URL); modifyConnectionString(connType, conn, 0); c = (HttpConnection) Connector.open(conn.toString()); int rc = c.getResponseCode(); if (rc != HttpConnection.HTTP_OK) { throw new IOException("HTTP Error: " + rc); } return c; } /** * * @param connType * @param conn * @param attemptWifi * @return true if the connection type provided can accept APN values. */ private static boolean modifyConnectionString(byte connType, StringBuffer conn, int timeout) { boolean apnOK = false; switch (connType) { case ConnectionHelper.CONNECTION_TYPE_TCP: // Socket connection. This is also the only one that acepts // additional APN connection info. conn.append(";deviceside=true"); apnOK = true; break; case ConnectionHelper.CONNECTION_TYPE_BES: conn.append(";deviceside=false"); if (timeout > 0) { conn.append(";ConnectionTimeout=").append(timeout * 1000); } break; case ConnectionHelper.CONNECTION_TYPE_WIFI: conn.append(";deviceside=true;interface=wifi"); break; case ConnectionHelper.CONNECTION_TYPE_WAP2: // Note that we've arlaedy validated that WAP2 is available. conn.append(";ConnectionUID=").append(getWAP2UID()); break; case ConnectionHelper.CONNECTION_TYPE_MDS_PUBLIC: conn.append(";deviceside=false;ConnectionType=mds-public;ConnectionTimeout=3600000"); break; } return apnOK; } // @todo - clean this up.. too, maybe just getConnection? public static void configureConnectionString(byte connType, StringBuffer conn, int timeout) { boolean apnOK = modifyConnectionString(connType, conn, timeout); if (!apnOK) { return; } Settings s = SettingsManager.getSettings(); String apn = s.getAPN(); String userName = s.getAPNUserName(); String password = s.getAPNPassword(); if (apn != null && apn.length() > 0) { conn.append(";apn=").append(apn); if (userName != null && userName.length() > 0) { conn.append(";tunnelauthusername=").append(userName); if (password != null && password.length() > 0) { conn.append(";tunnelauthpassword=").append(password); } } } } /** * Find WAP2 service book and return its UID. Note that it does this first by specifiying WPTCP records, then taking * the first active record that is NOT wifi and NOT mms. * * @return UID of WAP2 servicebook, or null if none exists. */ public static String getWAP2UID() { ServiceBook sb = ServiceBook.getSB(); ServiceRecord[] records = sb.findRecordsByCid("WPTCP"); String uid = null; for (int i = records.length - 1; i >= 0; i--) { if (records[i].isValid() && !records[i].isDisabled()) { // we assume here that getUid can't return null. String id = records[i].getUid().toLowerCase(); if (id.indexOf("wifi") == -1 && id.indexOf("mms") == -1) { // @todo -- need someone to test this who has an ISP that allows unusual ports. uid = records[i].getUid(); break; } } } return uid; } // not currently in use, a the service book name seems to vary internationally public static boolean isMDSPublicSupported() { // @todo : return CoverageInfo.isCoverageSufficient(CoverageInfo.COVERAGE_MDS))? ServiceBook sb = ServiceBook.getSB(); ServiceRecord[] records = sb.findRecordsByCid("IPPP"); if (records != null) { for (int i = records.length - 1; i >= 0; i--) { ServiceRecord rec = records[i]; if (rec.isValid() && !rec.isDisabled() && rec.getName().toLowerCase().indexOf("bibs") > 0) { return true; } } } return false; } /** * * @return true if wifi is enabled and currently connected. */ public static boolean isWifiAvailable() { return ((WLANInfo.getWLANState() == WLANInfo.WLAN_STATE_CONNECTED) && RadioInfo .areWAFsSupported(RadioInfo.WAF_WLAN)); } public static int getPermissionForConnType(int i) { switch (i) { case ConnectionHelper.CONNECTION_TYPE_MDS_PUBLIC: case ConnectionHelper.CONNECTION_TYPE_WAP2: case ConnectionHelper.CONNECTION_TYPE_TCP: return ApplicationPermissions.PERMISSION_EXTERNAL_CONNECTIONS; case ConnectionHelper.CONNECTION_TYPE_BES: return ApplicationPermissions.PERMISSION_INTERNAL_CONNECTIONS; case ConnectionHelper.CONNECTION_TYPE_WIFI: return ApplicationPermissions.PERMISSION_WIFI; } return 0; } }