#13795: Initial commit for sflphone-android
includes: libexpat libyaml libdbus-c++ commoncpp ccrtp
libdbus (from android-4.0.4 sources)
TODO:
- git ignores "/jni/sflphone", sflphone repo should be cloned.
- sflphone-android only needs daemon directory. Ideally it should be possible
to clone it without cloning the whole sflphone project.
into sfl-android (commit 6a0fa7a "#13961: Fix cipher handling" has been used here)
- add pjsip-android project as a git submodule
- sflphone-android needs pjsip android project. Ideally daemon git repository
should not embed pjsip. Instead pjsip should be clone from official repositories.
Considering this, structure should have three distincts git repos:
sflphone-android/.git
sflphone-android/jni/ccrtp-1.8.0-android
sflphone-android/jni/commoncpp2-1.8.1-android
sflphone-android/jni/dbus
sflphone-android/jni/libdbus-c++-0.9.0-android
sflphone-android/jni/libexpat
sflphone-android/jni/libyaml
sflphone-android/jni/sflphone-daemon/.git
sflphone-android/jni/sflphone-daemon/src/audio
sflphone-android/jni/sflphone-daemon/src/config
sflphone-android/jni/sflphone-daemon/src/dbus
sflphone-android/jni/sflphone-daemon/src/history
sflphone-android/jni/sflphone-daemon/src/hooks
sflphone-android/jni/sflphone-daemon/src/iax
sflphone-android/jni/sflphone-daemon/src/sip
sflphone-android/jni/sflphone-daemon/src/video
sflphone-android/jni/pjsip-android/.git
Signed-off-by: Emeric Vigier <emeric.vigier@savoirfairelinux.com>
diff --git a/jni/commoncpp2-1.8.1-android/src/url.cpp b/jni/commoncpp2-1.8.1-android/src/url.cpp
new file mode 100644
index 0000000..8880b79
--- /dev/null
+++ b/jni/commoncpp2-1.8.1-android/src/url.cpp
@@ -0,0 +1,866 @@
+// Copyright (C) 2001-2005 Open Source Telecom Corporation.
+// Copyright (C) 2006-2010 David Sugar, Tycho Softworks.
+//
+// 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.
+//
+// As a special exception, you may use this file as part of a free software
+// library without restriction. Specifically, if other files instantiate
+// templates or use macros or inline functions from this file, or you compile
+// this file and link it with other files to produce an executable, this
+// file does not by itself cause the resulting executable to be covered by
+// the GNU General Public License. This exception does not however
+// invalidate any other reasons why the executable file might be covered by
+// the GNU General Public License.
+//
+// This exception applies only to the code released under the name GNU
+// Common C++. If you copy code from other releases into a copy of GNU
+// Common C++, as the General Public License permits, the exception does
+// not apply to the code that you add in this way. To avoid misleading
+// anyone as to the status of such modified files, you must delete
+// this exception notice from them.
+//
+// If you write modifications of your own for GNU Common C++, it is your choice
+// whether to permit this exception to apply to your modifications.
+// If you do not wish that, delete this exception notice.
+//
+
+#include <cc++/config.h>
+#ifdef CCXX_WITHOUT_EXTRAS
+#include <cc++/export.h>
+#endif
+#include <cc++/file.h>
+#include <cc++/thread.h>
+#include <cc++/exception.h>
+#include <cc++/address.h>
+#include <cc++/socket.h>
+#ifndef CCXX_WITHOUT_EXTRAS
+#include <cc++/export.h>
+#endif
+#include <cc++/url.h>
+
+#include <string>
+#include <cstdio>
+#include <cstdlib>
+#include <fcntl.h>
+#include <cerrno>
+#include <iostream>
+
+#ifdef WIN32
+#include <io.h>
+#endif
+
+#ifdef HAVE_SSTREAM
+#include <sstream>
+#else
+#include <strstream>
+#endif
+
+#include <cctype>
+
+#ifndef WIN32
+// cause problem on Solaris
+#if !defined(__sun) && !defined(__SUN__)
+#ifdef HAVE_NET_IF_H
+#include <net/if.h>
+#endif
+#endif
+#include <sys/ioctl.h>
+#endif
+
+#ifdef CCXX_NAMESPACES
+namespace ost {
+using namespace std;
+#endif
+
+URLStream::URLStream(Family fam, timeout_t to) :
+TCPStream(fam)
+{
+ persistent = false;
+ proxyPort = 0;
+ timeout = to;
+ protocol = protocolHttp1_0;
+ follow = true;
+ proxyAuth = authAnonymous;
+ encoding = encodingBinary;
+ proxyUser = proxyPasswd = NULL;
+ auth = authAnonymous;
+ cookie = agent = pragma = referer = user = password = NULL;
+ localif = NULL;
+ setError(false);
+}
+
+int URLStream::aRead(char *buffer, size_t len, timeout_t timer)
+{
+ return readData(buffer, len, 0, timer);
+}
+
+int URLStream::aWrite(char *buffer, size_t len, timeout_t timer)
+{
+ return writeData(buffer, len, timer);
+}
+
+void URLStream::httpHeader(const char *header, const char *value)
+{
+}
+
+char **URLStream::extraHeader(void)
+{
+ return NULL;
+}
+
+int URLStream::underflow(void)
+{
+ ssize_t len = 0, rlen;
+ char *buf;
+
+ if(bufsize == 1)
+ return TCPStream::underflow();
+
+ if(!gptr())
+ return EOF;
+
+ if(gptr() < egptr())
+ return (unsigned char)*gptr();
+
+ rlen = (ssize_t)((gbuf + bufsize) - eback());
+ if(encoding == encodingChunked) {
+ buf = (char *)eback();
+ *buf = '\n';
+ while(!chunk && (*buf == '\n' || *buf == '\r')) {
+ *buf = 0;
+ len = readLine(buf, rlen, timeout);
+ }
+ if(len) {
+ if(!chunk)
+ chunk = strtol(buf, NULL, 16);
+
+ if(rlen > (int)chunk)
+ rlen = chunk;
+ }
+ else
+ rlen = -1;
+ }
+
+ if(rlen > 0) {
+ if(Socket::state == STREAM)
+ rlen = aRead((char *)eback(), rlen, timeout);
+ else if(timeout) {
+ if(Socket::isPending(pendingInput, timeout))
+ rlen = readData(eback(), rlen);
+ else
+ rlen = -1;
+ }
+ else
+ rlen = readData(eback(), rlen);
+ }
+ if(encoding == encodingChunked && rlen > 0)
+ chunk -= rlen;
+
+ if(rlen < 1) {
+ if(rlen < 0)
+ clear(ios::failbit | rdstate());
+ return EOF;
+ }
+ setg(eback(), eback(), eback() + rlen);
+ return (unsigned char)*gptr();
+}
+
+void URLStream::setProxy(const char *host, tpport_t port)
+{
+ switch(family) {
+#ifdef CCXX_IPV6
+ case IPV6:
+ v6proxyHost = host;
+ break;
+#endif
+ case IPV4:
+ proxyHost = host;
+ break;
+ default:
+ proxyPort = 0;
+ return;
+ }
+ proxyPort = port;
+}
+
+URLStream::Error URLStream::submit(const char *path, const char **vars, size_t buf)
+{
+ Error status = errInvalid, saved;
+
+ if(!strnicmp(path, "http:", 5)) {
+ urlmethod = methodHttpGet;
+ path = strchr(path + 5, '/');
+ status = sendHTTPHeader(path, vars, buf);
+ }
+ if((status == errInvalid || status == errTimeout)) {
+ if(Socket::state != AVAILABLE)
+ close();
+ return status;
+ }
+ else {
+ saved = status;
+ status = getHTTPHeaders();
+ if(status == errSuccess)
+ return saved;
+ else if(status == errTimeout) {
+ if(Socket::state != AVAILABLE)
+ close();
+ }
+ return status;
+ }
+}
+
+URLStream::Error URLStream::post(const char *path, MIMEMultipartForm &form, size_t buf)
+{
+ Error status = errInvalid, saved;
+ if(!strnicmp(path, "http:", 5)) {
+ urlmethod = methodHttpPostMultipart;
+ path = strchr(path + 5, '/');
+ status = sendHTTPHeader(path, (const char **)form.getHeaders(), buf);
+ }
+
+ if(status == errInvalid || status == errTimeout) {
+ if(Socket::state != AVAILABLE)
+ close();
+ return status;
+ }
+ saved = status;
+ status = getHTTPHeaders();
+ if(status == errSuccess) {
+ form.body(dynamic_cast<std::ostream *>(this));
+ return saved;
+ }
+ if(status == errTimeout) {
+ if(Socket::state != AVAILABLE)
+ close();
+ }
+ return status;
+}
+
+URLStream::Error URLStream::post(const char *path, const char **vars, size_t buf)
+{
+ Error status = errInvalid, saved;
+
+ if(!strnicmp(path, "http:", 5)) {
+ urlmethod = methodHttpPost;
+ path = strchr(path + 5, '/');
+ status = sendHTTPHeader(path, vars, buf);
+ }
+
+ if((status == errInvalid || status == errTimeout)) {
+ if(Socket::state != AVAILABLE)
+ close();
+ return status;
+ }
+ saved = status;
+ status = getHTTPHeaders();
+ if(status == errSuccess)
+ return saved;
+ if(status == errTimeout) {
+ if(Socket::state != AVAILABLE)
+ close();
+ }
+ return status;
+}
+
+
+URLStream::Error URLStream::head(const char *path, size_t buf)
+{
+ Error status = errInvalid, saved;
+
+ if(!strnicmp(path, "http:", 5)) {
+ urlmethod = methodHttpGet;
+ path = strchr(path + 5, '/');
+ status = sendHTTPHeader(path, NULL, buf);
+ }
+
+ if((status == errInvalid || status == errTimeout)) {
+ if(Socket::state != AVAILABLE)
+ close();
+ return status;
+ }
+ else {
+ saved = status;
+ status = getHTTPHeaders();
+ if(status == errSuccess)
+ return saved;
+ else if(status == errTimeout) {
+ if(Socket::state != AVAILABLE)
+ close();
+ }
+ return status;
+ }
+}
+
+URLStream &URLStream::getline(char *buffer, size_t size)
+{
+ size_t len;
+
+ *buffer = 0;
+ // TODO: check, we mix use of streambuf with Socket::readLine...
+ iostream::getline(buffer, (unsigned long)size);
+ len = strlen(buffer);
+
+ while(len) {
+ if(buffer[len - 1] == '\r' || buffer[len - 1] == '\n')
+ buffer[len - 1] = 0;
+ else
+ break;
+ --len;
+ }
+ return *this;
+}
+
+URLStream::Error URLStream::get(size_t buffer)
+{
+ String path = String("http://") + m_host;
+
+ if ( m_address.operator[](0) != '/' )
+ path += "/";
+
+ path += m_address;
+
+ return get(path.c_str(), buffer);
+}
+
+URLStream::Error URLStream::get(const char *urlpath, size_t buf)
+{
+ const char *path = urlpath;
+ Error status = errInvalid, saved;
+
+ urlmethod = methodFileGet;
+
+ if(Socket::state != AVAILABLE)
+ close();
+
+
+ if(!strnicmp(path, "file:", 5)) {
+ urlmethod = methodFileGet;
+ path += 5;
+ }
+ else if(!strnicmp(path, "http:", 5)) {
+ urlmethod = methodHttpGet;
+ path = strchr(path + 5, '/');
+ }
+ switch(urlmethod) {
+ case methodHttpGet:
+ status = sendHTTPHeader(path, NULL, buf);
+ break;
+ case methodFileGet:
+ if(so != INVALID_SOCKET)
+ ::close((int)so);
+ so = ::open(path, O_RDWR);
+ if(so == INVALID_SOCKET)
+ so = ::open(path, O_RDONLY);
+ // FIXME: open return the same handle type as socket call ??
+ if(so == INVALID_SOCKET)
+ return errInvalid;
+ Socket::state = STREAM;
+ allocate(buf);
+ return errSuccess;
+ default:
+ break;
+ }
+
+
+ if((status == errInvalid || status == errTimeout)) {
+ if(Socket::state != AVAILABLE)
+ close();
+ return status;
+ }
+ else {
+ saved = status;
+ status = getHTTPHeaders();
+ if(status == errSuccess)
+ return saved;
+ else if(status == errTimeout) {
+ if(Socket::state != AVAILABLE)
+ close();
+ }
+ return status;
+ }
+}
+
+URLStream::Error URLStream::getHTTPHeaders()
+{
+ char buffer[512];
+ size_t buf = sizeof(buffer);
+ Error status = errSuccess;
+ char *cp, *ep;
+ ssize_t len = 1;
+ char nc = 0;
+
+ chunk = ((unsigned)-1) / 2;
+ encoding = encodingBinary;
+ while(len > 0) {
+ len = readLine(buffer, buf, timeout);
+ if(len < 1)
+ return errTimeout;
+
+ // FIXME: for multiline syntax ??
+ if(buffer[0] == ' ' || buffer[0] == '\r' || buffer[0] == '\n')
+ break;
+ cp = strchr(buffer, ':');
+ if(!cp)
+ continue;
+ *(cp++) = 0;
+ while(*cp == ' ' || *cp == '\t')
+ ++cp;
+ ep = strchr(cp, '\n');
+ if(!ep)
+ ep = &nc;
+ while(*ep == '\n' || *ep == '\r' || *ep == ' ') {
+ *ep = 0;
+ if((--ep) < cp)
+ break;
+ }
+ if(!stricmp(buffer, "Transfer-Encoding")) {
+ if(!stricmp(cp, "chunked")) {
+ chunk = 0;
+ encoding = encodingChunked;
+ }
+ }
+ httpHeader(buffer, cp);
+ }
+ return status;
+}
+
+
+void URLStream::close(void)
+{
+ if(Socket::state == AVAILABLE)
+ return;
+
+ endStream();
+ so = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);
+ if(so != INVALID_SOCKET)
+ Socket::state = AVAILABLE;
+}
+
+URLStream::Error URLStream::sendHTTPHeader(const char *url, const char **vars, size_t buf)
+{
+ // TODO: implement authentication
+ char reloc[4096];
+ // "//" host ":" port == max 2 + 128 + 1 + 5 + 1(\0) = 137, rounded 140
+ char host[140];
+ // TODO: add support for //user:pass@host:port/ syntax
+#ifdef HAVE_SSTREAM
+ ostringstream str;
+#else
+ char buffer[4096];
+ strstream str(buffer, sizeof(buffer), ios::out);
+#endif
+ char *ref, *cp, *ep;
+ char *hp;
+ const char *uri = "/";
+ int count = 0;
+ size_t len = 0;
+ tpport_t port = 80;
+ const char **args = vars;
+ const char *var;
+ bool lasteq = true;
+
+ struct servent *svc;
+
+retry:
+#ifdef HAVE_SSTREAM
+ str.str("");
+#else
+ buffer[0] = 0;
+ str.seekp(0);
+#endif
+
+ setString(host, sizeof(host), url);
+reformat:
+ hp = strchr(host, '/');
+ if(!hp) {
+ host[0] = '/';
+ setString(host + 1, sizeof(host) - 1, url);
+ goto reformat;
+ }
+ while(*hp == '/')
+ ++hp;
+ cp = strchr(hp, '/');
+ if (cp) *cp = 0;
+ ep = strrchr(hp, ':');
+ if(ep) {
+ *ep = 0;
+ ++ep;
+ if(isdigit(*ep))
+ port = atoi(ep);
+ else {
+ Socket::mutex.enter();
+ svc = getservbyname(ep, "tcp");
+ if(svc)
+ port = ntohs(svc->s_port);
+ Socket::mutex.leave();
+ }
+ }
+
+ if(!proxyPort) {
+ const char* ep1 = url;
+ while(*ep1 == '/')
+ ++ep1;
+ ep1 = strchr(ep1, '/');
+ if(ep1)
+ uri = ep1;
+ }
+
+ switch(urlmethod) {
+ case methodHttpGet:
+ str << "GET ";
+ if(proxyPort) {
+ str << "http:" << url;
+ if(!cp) str << '/';
+ }
+ else
+ str << uri;
+ break;
+ case methodHttpPost:
+ case methodHttpPostMultipart:
+ str << "POST ";
+ if(proxyPort) {
+ str << "http:" << url;
+ if(!cp) str << '/';
+ }
+ else
+ str << uri;
+ break;
+ default:
+ return errInvalid;
+ }
+
+ if(vars && urlmethod == methodHttpGet) {
+ str << "?";
+ while(*vars) {
+ if(count++ && lasteq)
+ str << "&";
+ str << *vars;
+ if(!lasteq)
+ lasteq = true;
+ else if(strchr(*vars, '='))
+ lasteq = true;
+ else {
+ lasteq = false;
+ str << "=";
+ }
+ ++vars;
+ }
+ }
+
+ switch(protocol) {
+ case protocolHttp1_1:
+ str << " HTTP/1.1" << "\r\n";
+ break;
+ case protocolHttp1_0:
+ str << " HTTP/1.0" << "\r\n";
+ break;
+ }
+
+ if ( m_host.empty() )
+ m_host = hp;
+
+ str << "Host: " << hp << "\r\n";
+ if(agent)
+ str << "User-Agent: " << agent << "\r\n";
+
+ if(cookie)
+ str << "Cookie: " << cookie << "\r\n";
+
+ if(pragma)
+ str << "Pragma: " << pragma << "\r\n";
+
+ if(referer)
+ str << "Referer: " << referer << "\r\n";
+
+ switch(auth) {
+ case authBasic:
+ str << "Authorization: Basic ";
+ snprintf(reloc, 64, "%s:%s", user, password);
+ b64Encode(reloc, reloc + 64, 128);
+ str << reloc + 64 << "\r\n";
+ case authAnonymous:
+ break;
+ }
+
+ switch(proxyAuth) {
+ case authBasic:
+ str << "Proxy-Authorization: Basic ";
+ snprintf(reloc, 64, "%s:%s", proxyUser, proxyPasswd);
+ b64Encode(reloc, reloc + 64, 128);
+ str << reloc + 64 << "\r\n";
+ str << "Proxy-Connection: close" << "\r\n";
+ case authAnonymous:
+ break;
+ }
+
+
+ str << "Connection: close\r\n";
+ char **add = extraHeader();
+ if(add) {
+ while(*add) {
+ str << *(add++) << ": ";
+ str << *(add++) << "\r\n";
+ }
+ }
+ if(vars)
+ switch(urlmethod) {
+ case methodHttpPost:
+ while(*args) {
+ var = *args;
+ if(count++ || !strchr(var, '='))
+ len += strlen(var) + 1;
+ else
+ len = strlen(var);
+ ++args;
+ }
+ count = 0;
+ len += 2;
+ str << "Content-Type: application/x-www-form-urlencoded" << "\r\n";
+ str << "Content-Length: " << (unsigned)len << "\r\n";
+ break;
+ case methodHttpPostMultipart:
+ while(*args)
+ str << *(args++) << "\r\n";
+ default:
+ break;
+ }
+
+ str << "\r\n";
+#ifdef HAVE_SSTREAM
+ // sstream does not want ends
+#else
+ str << ends;
+#endif
+
+ if(Socket::state != AVAILABLE)
+ close();
+#ifndef WIN32
+#ifdef SOICGIFINDEX
+ if (localif != NULL) {
+ struct ifreq ifr;
+
+ switch(family) {
+#ifdef CCXX_IPV6
+ case IPV6:
+ sockaddr_in6 source;
+ int alen = sizeof(source);
+
+ memset(&ifr, 0, sizeof(ifr));
+ setString(ifr.ifr_name, sizeof(ifr.ifr_name), localif);
+ if (ioctl(so, SIOCGIFINDEX, &ifr) < 0)
+ return errInterface;
+ else {
+ if (setsockopt(so, SOL_SOCKET, SO_BINDTODEVICE, &ifr, sizeof(ifr)) == -1)
+ return errInterface;
+ else if(getsockname(so, (struct sockaddr*)&source,(socklen_t *) &alen) == -1)
+ return errInterface;
+ else if (bind(so, (struct sockaddr*)&source, sizeof(source)) == -1)
+ return errInterface;
+ else
+ source.sin6_port = 0;
+ }
+
+ break;
+#endif
+ case IPV4:
+ sockaddr_in source;
+ int alen = sizeof(source);
+
+ memset(&ifr, 0, sizeof(ifr));
+ setString(ifr.ifr_name, sizeof(ifr.ifr_name), localif);
+ if (ioctl(so, SIOCGIFINDEX, &ifr) < 0)
+ return errInterface;
+ else {
+ if (setsockopt(so, SOL_SOCKET, SO_BINDTODEVICE, &ifr, sizeof(ifr)) == -1)
+ return errInterface;
+ else if(getsockname(so, (struct sockaddr*)&source,(socklen_t *) &alen) == -1)
+ return errInterface;
+ else if (bind(so, (struct sockaddr*)&source, sizeof(source)) == -1)
+ return errInterface;
+ else
+ source.sin_port = 0;
+ }
+ }
+
+ }
+#endif
+#endif
+
+ if(proxyPort) {
+ switch(family) {
+#ifdef CCXX_IPV6
+ case IPV6:
+ connect(v6proxyHost, proxyPort, (unsigned)buf);
+ break;
+#endif
+ case IPV4:
+ connect(proxyHost, proxyPort, (unsigned)buf);
+ break;
+ }
+ }
+ else {
+ switch(family) {
+#ifdef CCXX_IPV6
+ case IPV6:
+ connect(IPV6Host(hp), port, (unsigned)buf);
+ break;
+#endif
+ case IPV4:
+ connect(IPV4Host(hp), port, (unsigned)buf);
+ }
+ }
+
+ if(!isConnected())
+ return errUnreachable;
+
+ // FIXME: send (or write) can send less than len bytes
+ // use stream funcion ??
+#ifdef HAVE_SSTREAM
+ writeData(str.str().c_str(), _IOLEN64 str.str().length());
+#else
+ writeData(str.str().c_str(), _IOLEN64 str.str().length());
+#endif
+
+ if(urlmethod == methodHttpPost && vars) {
+#ifdef HAVE_SSTREAM
+ str.str() = "";
+#else
+ str.seekp(0);
+#endif
+ bool sep = false;
+ while(*vars) {
+ if(sep)
+ writeData("&", 1);
+ else
+ sep = true;
+ var = *vars;
+ if(!strchr(var, '=')) {
+ snprintf(reloc, sizeof(reloc), "%s=%s", var, *(++vars));
+ writeData(reloc, strlen(reloc));
+ }
+ else
+ writeData(var, strlen(var));
+ ++vars;
+ }
+ writeData("\r\n", 2);
+ }
+
+cont:
+#ifdef HAVE_SSTREAM
+ char buffer[4096];
+#else
+ // nothing here
+#endif
+
+ len = readLine(buffer, sizeof(buffer) - 1, timeout);
+ if(len < 1)
+ return errTimeout;
+
+ if(strnicmp(buffer, "HTTP/", 5))
+ return errInvalid;
+
+ ref = strchr(buffer, ' ');
+ while(*ref == ' ')
+ ++ref;
+
+ switch(atoi(ref)) {
+ default:
+ return errInvalid;
+ case 100:
+ goto cont;
+ case 200:
+ return errSuccess;
+ case 401:
+ return errUnauthorized;
+ case 403:
+ return errForbidden;
+ case 404:
+ return errMissing;
+ case 405:
+ return errDenied;
+ case 500:
+ case 501:
+ case 502:
+ case 503:
+ case 504:
+ case 505:
+ return errFailure;
+ case 300:
+ case 301:
+ case 302:
+ break;
+ }
+ if(!follow)
+ return errRelocated;
+ for(;;) {
+ len = readLine(reloc, sizeof(reloc), timeout);
+ if(len < 1)
+ return errTimeout;
+ if(!strnicmp(reloc, "Location: ", 10))
+ break;
+ }
+ if(!strnicmp(reloc + 10, "http:", 5)) {
+ url = strchr(reloc + 15, '/');
+ ep = (char *)(url + strlen(url) - 1);
+ while(*ep == '\r' || *ep == '\n')
+ *(ep--) = 0;
+ }
+ else
+ url = reloc + 10;
+ close();
+ goto retry;
+}
+
+void URLStream::setAuthentication(Authentication a, const char *value)
+{
+ auth = a;
+ if (auth != authAnonymous) {
+ if(!user)
+ user = "anonymous";
+ if(!password)
+ password = "";
+ }
+}
+
+void URLStream::setProxyAuthentication(Authentication a, const char *value)
+{
+ proxyAuth = a;
+ if (proxyAuth != authAnonymous) {
+ if(!proxyUser)
+ proxyUser = "anonymous";
+
+ if(!proxyPasswd)
+ proxyPasswd = "";
+ }
+}
+
+void URLStream::setReferer(const char *str)
+{
+ if(!str)
+ return;
+ referer = str;
+}
+
+#ifdef CCXX_NAMESPACES
+}
+#endif
+
+/** EMACS **
+ * Local variables:
+ * mode: c++
+ * c-basic-offset: 4
+ * End:
+ */