/********************************************************************
* lindner
* 3.16
* 1995/02/06 22:10:47
* /home/arcwelder/GopherSrc/CVS/gopher+/object/url.c,v
* Exp
*
* Paul Lindner, University of Minnesota CIS.
*
* Copyright 1991, 1992 by the Regents of the University of Minnesota
* see the file "Copyright" in the distribution for conditions of use.
*********************************************************************
* MODULE: url.c
* Simplified method of getting urls..
*********************************************************************
* Revision History:
* url.c,v
* Revision 3.16 1995/02/06 22:10:47 lindner
* Fix for systems without strstr, compiler casts
*
* Revision 3.15 1994/12/05 22:47:19 lindner
* Fixed settings of Gopher Type in URLparse()
*
* Revision 3.14 1994/11/18 22:45:55 lindner
* Remove unused variable
*
* Revision 3.13 1994/11/18 21:41:48 lindner
* Fix order of FTP arguments
*
* Revision 3.12 1994/11/13 06:30:06 lindner
* Expanded URL parsing routines
*
* Revision 3.11 1994/10/13 05:25:56 lindner
* Compiler complaint fixes
*
* Revision 3.10 1994/08/19 16:28:30 lindner
* More hexification of URL strings
*
* Revision 3.9 1994/07/25 03:51:41 lindner
* Compiler fix
*
* Revision 3.8 1994/07/21 22:17:20 lindner
* Add ftp urls
*
* Revision 3.7 1994/03/04 17:42:57 lindner
* Fixes from Alan Coopersmith
*
* Revision 3.6 1994/01/21 04:25:41 lindner
* Add support for tn3270 and better gopher url handling
*
* Revision 3.5 1993/12/30 04:18:08 lindner
* translate telnet url correctly
*
* Revision 3.4 1993/12/27 16:14:03 lindner
* Enlarge buffer size, make html docs on gopher server into http: refs
*
* Revision 3.3 1993/11/02 06:14:09 lindner
* Add url html hack
*
*
*********************************************************************/
#include "url.h"
#include "GSgopherobj.h"
#include "Malloc.h"
#include "String.h"
#include "compatible.h"
Url *
URLnew()
{
Url *temp;
temp = (Url *) malloc(sizeof(Url));
temp->url = STRnew();
temp->Host = STRnew();
temp->Port = -1;
temp->Path = STRnew();
temp->User = STRnew();
temp->Pass = STRnew();
temp->Gtype = '\0';
URLsetService(temp, unset);
return(temp);
}
void
URLdestroy(url)
Url *url;
{
STRdestroy(url->url);
STRdestroy(url->Host);
STRdestroy(url->Path);
STRdestroy(url->User);
STRdestroy(url->Pass);
free(url);
}
/*
* Make a default url from the current Gopher Object...
*/
void
URLfromGS(url, gs)
Url *url;
GopherObj *gs;
{
char u[2048], *path, *cp;
*u = '\0';
path = GSgetPath(gs);
if (GSgetHost(gs) == NULL)
return;
if ((GSgetType(gs) == A_TN3270) || (GSgetType(gs) == A_TELNET)) {
/* [telnet|tn3270]://[host]@[login]:[port] */
if (GSgetType(gs) == A_TELNET)
strcpy(u,"telnet://");
else
strcpy(u,"tn3270://");
Tohexstr(GSgetHost(gs), u + 9);
if ( (path != NULL) && (*path != '\0') ) {
cp = u + strlen(u);
*(cp++) = '@';
Tohexstr(path, cp);
}
sprintf(u + strlen(u), ":%d", GSgetPort(gs));
}
else if (path != NULL)
{
if (strncmp(path, "GET /", 5) == 0) {
/* http://[host]:[port][path without "GET "] */
strcpy(u, "http://");
Tohexstr(GSgetHost(gs), u+7);
sprintf(u + strlen(u), ":%d", GSgetPort(gs));
Tohexstr(path + 4, u + strlen(u));
} else if (strncmp(path, "ftp:", 4) == 0) {
/** ftp://[host]/[pathname]; **/
char *atsign;
strcpy(u, "ftp://");
strcat(u, path + 4);
atsign = strchr(u, '@');
if (atsign != NULL)
Tohexstr( path + (atsign-u)-1, atsign );
} else {
/* gopher://[host]:[port]/[type][path] */
strcpy(u, "gopher://");
Tohexstr(GSgetHost(gs), u + 9);
sprintf(u + strlen(u), ":%d/%c", GSgetPort(gs), GSgetType(gs));
Tohexstr(path, u + strlen(u));
}
}
URLset(url, u);
}
/*
* Hack gopher directories into an HTML type...
*/
void
URLmakeHTML(url)
Url *url;
{
char *cp = URLget(url);
if (cp == NULL)
return;
if (strncmp(cp, "gopher://", 9) != 0)
return;
/** find the type character **/
cp = strchr(cp+10, '/');
if (cp ==NULL)
return;
/** Test link for current host **/
/* host = cp+10;
if (strcasecmp(host, hostname) != 0)
return;*/
cp ++;
/** cp is now pointed at the type character **/
if (*cp == '1' && *(cp+1) == '1') {
/** It's a directory **/
*cp = 'h';
*(cp+1) = 'h';
}
}
/*
* Get the transport of the specified URL
*/
UrlServiceType
URLgetService(url)
Url *url;
{
UrlServiceType st;
if (url->service == unset) {
char *urlcp;
urlcp = URLget(url);
if (urlcp == NULL)
return(unknown);
st = unknown;
if (strncasecmp("ftp:", urlcp, 4)==0)
st = ftp;
else if (strncasecmp(urlcp, "gopher:", 7)==0)
st = gopher;
else if (strncasecmp(urlcp, "telnet:", 7)==0)
st = telnet;
else if (strncasecmp(urlcp, "tn3270:", 7)==0)
st = tn3270;
else if (strncasecmp(urlcp, "http:", 5)==0)
st = http;
URLsetService(url, st);
}
return(url->service);
}
static boolean
URLparse(url)
Url *url;
{
char *cp, *cp2, *cp3, *urlcp;
UrlServiceType serviceType;
serviceType = URLgetService(url);
if (serviceType == unknown)
return(FALSE);
urlcp = URLget(url);
if (urlcp == NULL)
return(FALSE);
urlcp = strdup(urlcp); /* This lets us scribble on the string */
cp = strstr(urlcp, "://"); /* skip over servicetype + "://" */
if (cp == NULL)
return(FALSE);
cp += 3;
cp3 = strchr(cp, '/'); /* end of login:passwd@host:port/ section */
if (cp3 == NULL) {
cp3 = cp + strlen(cp) + 1; /* No slash at the end... */
URLsetPath(url, "\0");
} else {
*cp3 = '\0';
cp3++;
Fromhexstr(cp3, cp3);
URLsetPath(url,cp3);
}
if (serviceType == gopher) {
if (cp3 != NULL && (int)strlen(cp3) > 1) {
URLsetGophType(url, *(cp3++));
URLsetPath(url,cp3++);
}
else
URLsetGophType(url, '1');
}
/*
* Find Username/pass for ftp/telnet
*/
cp2 = strchr(cp, '@');
if ((cp2 != NULL) && (cp2 < cp3)) {
char *pass;
*cp2 = '\0';
cp2++;
pass = strchr(cp, ':');
if ((pass != NULL) && (pass < cp3)) {
*pass = '\0';
pass++;
Fromhexstr(pass, pass);
URLsetPass(url, pass);
}
URLsetUser(url, cp);
cp = cp2; /** cp now points to hostname **/
}
/*
* Find port
*/
cp2 = strchr(cp, ':');
if ((cp2 != NULL) && (cp2 < cp3)) {
*cp2 = '\0';
cp2++;
URLsetPort(url, atoi(cp2));
URLsetHost(url, cp);
} else {
switch (serviceType) {
case http:
URLsetPort(url, 80);
break;
case telnet:
case tn3270:
URLsetPort(url, 23);
break;
case gopher:
URLsetPort(url, 70);
break;
case news:
URLsetPort(url, 119);
break;
}
URLsetHost(url, cp);
}
return(TRUE);
}
char *
URLgetHost(url)
Url *url;
{
if (STRget(url->Host) == NULL)
URLparse(url);
return(STRget(url->Host));
}
int
URLgetPort(url)
Url *url;
{
if (url->Port == -1)
URLparse(url);
return(url->Port);
}
char *
URLgetPath(url)
Url *url;
{
if (STRget(url->Path) == NULL)
URLparse(url);
return(STRget(url->Path));
}
char *
URLgetUser(url)
Url *url;
{
if (STRget(url->User) == NULL)
URLparse(url);
return(STRget(url->User));
}
char *
URLgetPass(url)
Url *url;
{
if (STRget(url->Pass) == NULL)
URLparse(url);
return(STRget(url->Pass));
}
char
URLgetGophType(url)
Url *url;
{
if (URLgetService(url) != gopher)
return('\0');
if (url->Gtype == '\0')
URLparse(url);
return(url->Gtype);
}