Exemple #1
0
/* Isolate the "CURL." prefix to allow changing to something else */
static char*
curllookup(char* suffix, char* url)
{
    char key[2048];
    char* value = NULL;
    if(!occopycat(key,sizeof(key),2,HTTPPREFIX,suffix))
	return NULL;
    value = ocdodsrc_lookup(key,url);
    if(value == NULL) {
        if(!occopycat(key,sizeof(key),2,HTTPPREFIXDEPRECATED,suffix))
	    return NULL;
        value = ocdodsrc_lookup(key,url);
    }
    return value;
}
Exemple #2
0
static int
readfile(const char* path, const char* suffix, OCbytes* packet)
{
    int stat = OC_NOERR;
    char buf[1024];
    char filename[1024];
    int fd = -1;
    int flags = 0;
    off_t filesize = 0;
    off_t totalread = 0;
    /* check for leading file:/// */
    if(ocstrncmp(path,"file://",7)==0) path += 7; /* assume absolute path*/
    if(!occopycat(filename,sizeof(filename),2,path,(suffix != NULL ? suffix : "")))
	return OCTHROW(OC_EOVERRUN);
    flags = O_RDONLY;
#ifdef O_BINARY
    flags |= O_BINARY;
#endif
    fd = open(filename,flags);
    if(fd < 0) {
	oclog(OCLOGERR,"open failed:%s",filename);
	return OCTHROW(OC_EOPEN);
    }
    /* Get the file size */
    filesize = lseek(fd,(off_t)0,SEEK_END);
    if(filesize < 0) {
	stat = OC_EIO;
	oclog(OCLOGERR,"lseek failed: %s",filename);
	goto done;
    }
    /* Move file pointer back to the beginning of the file */
    (void)lseek(fd,(off_t)0,SEEK_SET);
    stat = OC_NOERR;
    for(totalread=0;;) {
	off_t count = (off_t)read(fd,buf,sizeof(buf));
	if(count == 0)
	    break; /*eof*/
	else if(count <  0) {
	    stat = OC_EIO;
	    oclog(OCLOGERR,"read failed: %s",filename);
	    goto done;
	}
	ocbytesappendn(packet,buf,(unsigned long)count);
	totalread += count;
    }
    if(totalread < filesize) {
	stat = OC_EIO;
	oclog(OCLOGERR,"short read: |%s|=%lu read=%lu\n",
		filename,(unsigned long)filesize,(unsigned long)totalread);
        goto done;
    }

done:
#ifdef OCDEBUG
fprintf(stderr,"readfile: filesize=%lu totalread=%lu\n",
		(unsigned long)filesize,(unsigned long)totalread);
#endif
    if(fd >= 0) close(fd);
    return OCTHROW(stat);
}
Exemple #3
0
/*
    Set curl properties for link based on rc files
*/
static void
ocsetcurlproperties(OCstate* state)
{
    CURLcode cstat = CURLE_OK;

    /* process the triple store wrt to this state */
    if(ocdodsrc_process(state) != OC_NOERR) {
	oclog(OCLOGERR,"Malformed .opendaprc configuration file");
	goto fail;
    }
    if(state->creds.username == NULL && state->creds.password == NULL) {
        if(state->uri->user != NULL && state->uri->password != NULL) {
	    /* this overrides .dodsrc */
            if(state->creds.password) free(state->creds.password);
            state->creds.password = nulldup(state->uri->password);
            if(state->creds.username) free(state->creds.username);
            state->creds.username = nulldup(state->uri->user);
	}
    }
    if(state->curlflags.useragent == NULL) {
        size_t len = strlen(DFALTUSERAGENT) + strlen(VERSION) + 1;
	char* agent = (char*)malloc(len+1);
	if(occopycat(agent,len,2,DFALTUSERAGENT,VERSION))
	  state->curlflags.useragent = agent;
	else
	  free(agent);
    }
    return;

fail:
    if(cstat != CURLE_OK)
	oclog(OCLOGERR, "curl error: %s", curl_easy_strerror(cstat));
    return;
}
Exemple #4
0
char*
occombinehostport(const OCURI* uri)
{
    char* hp;
    int len = 0;

    if(uri->host == NULL)
	return NULL;
    else
	len += strlen(uri->host);
    if(uri->port != NULL)
	len += strlen(uri->port);
    hp = (char*)malloc(len+1);
    if(hp == NULL)
	return NULL;
    if(uri->port == NULL)
        occopycat(hp,len+1,1,uri->host);
    else
        occopycat(hp,len+1,3,uri->host,":",uri->port);
    return hp;
}
Exemple #5
0
int
ocmktmp(const char* base, char** tmpnamep, int* fdp)
{
    int fd;
    char* tmpname = NULL;
    mode_t oldmask;
    size_t tmpsize = strlen(base)+strlen("XXXXXX") + 1;

    tmpname = (char*)malloc(tmpsize);
    if(tmpname == NULL) return OC_ENOMEM;
    if(!occopycat(tmpname,tmpsize,1,base)) {
	free(tmpname);
	return OC_EOVERRUN;
    }
#ifdef HAVE_MKSTEMP
    if(!occoncat(tmpname,tmpsize,1,"XXXXXX")) {
        free(tmpname);
	return OC_EOVERRUN;
    }
    /* Note Potential problem: old versions of this function
       leave the file in mode 0666 instead of 0600 */
    oldmask= umask(S_IRUSR | S_IWUSR | S_IRGRP | S_IWGRP | S_IROTH | S_IWOTH);
    fd = mkstemp(tmpname);
    umask(oldmask); /* restore */
#else /* !HAVE_MKSTEMP */
    /* Need to simulate by using some kind of pseudo-random number */
    {
	int rno = rand();
	char spid[7];
	if(rno < 0) rno = -rno;
        snprintf(spid,sizeof(spid),"%06d",rno);
	if(!occoncat(tmpname,tmpsize,1,spid)) {
            free(tmpname);
	    return OC_EOVERRUN;
        }
#if defined(_WIN32) || defined(_WIN64)
        fd=open(tmpname,O_RDWR|O_BINARY|O_CREAT|O_EXCL|FILE_ATTRIBUTE_TEMPORARY, _S_IREAD|_S_IWRITE);
#  else
        fd=open(tmpname,O_RDWR|O_CREAT|O_EXCL, S_IRWXU);
#  endif
    }
#endif /* !HAVE_MKSTEMP */
    if(fd < 0) {
       if(tmpname != NULL) free(tmpname);
       return OC_EOPEN;
    }
    if(tmpnamep) *tmpnamep = tmpname;    
    else if(tmpname != NULL) {free(tmpname);}
    if(fdp) *fdp = fd;
    else if(fd >= 0) close(fd);
    return OC_NOERR;
}
Exemple #6
0
static char*
ocrc_lookup(char* suffix, char* url)
{
    char* value = NULL;
    char key[MAXRCLINESIZE+1];
    const char** p = prefixes;
    for(;*p;p++) {
        if(!occopycat(key,sizeof(key),2,*p,suffix))
            return NULL;
	value = ocrc_lookup(key,url);
	if(value != NULL)
	    return value;
    }
    return value;
}
Exemple #7
0
static char*
combinecredentials(const char* user, const char* pwd)
{
    int userPassSize;
    char *userPassword;

    if(user == NULL) user = "";
    if(pwd == NULL) pwd = "";

    userPassSize = strlen(user) + strlen(pwd) + 2;
    userPassword = malloc(sizeof(char) * userPassSize);
    if (!userPassword) {
        oclog(OCLOGERR,"Out of Memory\n");
	return NULL;
    }
    occopycat(userPassword,userPassSize-1,3,user,":",pwd);
    return userPassword;
}
Exemple #8
0
int
createtempfile1(char* tmppath, char** tmpnamep)
{
    int fd = 0;
    char* tmpname = NULL;
    size_t tmpsize = strlen(tmppath)+strlen("dataddsXXXXXX") + 1;
    tmpname = (char*)malloc(tmpsize);
    if(tmpname == NULL) return -1;
    if(!occopycat(tmpname,tmpsize,1,tmppath))
	return OC_EOVERRUN;
#ifdef HAVE_MKSTEMP
    if(!occoncat(tmpname,tmpsize,1,"dataddsXXXXXX"))
	return OC_EOVERRUN;
    /* Note Potential problem: old versions of this function
       leave the file in mode 0666 instead of 0600 */
    umask(S_IRUSR | S_IWUSR | S_IRGRP | S_IWGRP | S_IROTH | S_IWOTH);
    fd = mkstemp(tmpname);
#else /* !HAVE_MKSTEMP */
    /* Need to simulate by using some kind of pseudo-random number */
    if(!occoncat(tmpname,tmpsize,1,"datadds"))
	return OC_EOVERRUN;
    {
	int rno = rand();
	char spid[7];
	if(rno < 0) rno = -rno;
        snprintf(spid,sizeof(spid),"%06d",rno);
	if(!occoncat(tmpname,tmpsize,1,spid))
	    return OC_EOVERRUN;
#  ifdef _WIN32
        fd=open(tmpname,O_RDWR|O_BINARY|O_CREAT|O_EXCL|FILE_ATTRIBUTE_TEMPORARY, _S_IREAD|_S_IWRITE);
#  else
        fd=open(tmpname,O_RDWR|O_CREAT|O_EXCL, S_IRWXU);
#  endif
    }
#endif /* !HAVE_MKSTEMP */
    if(tmpname == NULL) return -1;
    if(tmpnamep) *tmpnamep = tmpname;
    else
      free(tmpname);
    return fd;
}
Exemple #9
0
static OCerror
createtempfile(OCstate* state, OCtree* tree)
{
    int stat = OC_NOERR;
    char* path = NULL;
    char* name = NULL;
    int len;

    len =
	  strlen(ocglobalstate.tempdir)
	  + 1 /* '/' */
	  + strlen(DATADDSFILE);
    path = (char*)malloc(len+1);
    if(path == NULL) return OC_ENOMEM;
    occopycat(path,len,3,ocglobalstate.tempdir,"/",DATADDSFILE);
    stat = ocmktmp(path,&name);
    free(path);
    if(stat != OC_NOERR) goto fail;
#ifdef OCDEBUG
    oclog(OCLOGNOTE,"oc_open: creating tmp file: %s",name);
#endif
    tree->data.filename = name; /* remember our tmp file name */
    name = NULL;
    tree->data.file = fopen(tree->data.filename,"w+");
    if(tree->data.file == NULL) return OC_EOPEN;
    /* unlink the temp file so it will automatically be reclaimed */
    if(ocdebug == 0) unlink(tree->data.filename);
    return stat;

fail:
    if(name != NULL) {
        oclog(OCLOGERR,"oc_open: attempt to create tmp file failed: %s",name);
	free(name);
    } else {
        oclog(OCLOGERR,"oc_open: attempt to create tmp file failed: NULL");
    }
    return OCTHROW(stat);
}
Exemple #10
0
/**
 * Prefix must end in '/'
 */
static
OCerror
rc_search(const char* prefix, const char* rcname, char** pathp)
{
    char* path = NULL;
    FILE* f = NULL;
    int plen = strlen(prefix);
    int rclen = strlen(rcname);
    OCerror stat = OC_NOERR;

    size_t pathlen = plen+rclen+1+1; /*+1 for '/' +1 for nul*/
    path = (char*)malloc(pathlen);
    if(path == NULL) {
	stat = OC_ENOMEM;
	goto done;
    }
    if(!occopycat(path,pathlen,3,prefix,"/",rcname)) {
        stat = OC_EOVERRUN;
	goto done;
    }
    /* see if file is readable */
    f = fopen(path,"r");
    if(f != NULL)
        oclog(OCLOGDBG, "Found rc file=%s",path);
done:
    if(f == NULL || stat != OC_NOERR) {
	if(path != NULL)
	    free(path);
	path = NULL;
    }
    if(f != NULL)
	fclose(f);
    if(pathp != NULL)
	*pathp = path;
    return OCTHROW(stat);
}
Exemple #11
0
/*
    Set curl properties for link based on rc files etc.
*/
static OCerror
ocset_curlproperties(OCstate* state)
{
    OCerror stat = OC_NOERR;

    /* extract the relevant triples int state */
    ocrc_process(state);

    if(state->curlflags.useragent == NULL) {
        size_t len = strlen(DFALTUSERAGENT) + strlen(VERSION) + 1;
	char* agent = (char*)malloc(len+1);
	if(occopycat(agent,len,2,DFALTUSERAGENT,VERSION))
	    state->curlflags.useragent = agent;
	else
	    free(agent);
    }

    /* Some servers (e.g. thredds and columbia) appear to require a place
       to put cookies in order for some security functions to work
    */
    if(state->curlflags.cookiejar != NULL
       && strlen(state->curlflags.cookiejar) == 0) {
	free(state->curlflags.cookiejar);
	state->curlflags.cookiejar = NULL;
    }

    if(state->curlflags.cookiejar == NULL) {
	/* If no cookie file was defined, define a default */
	char tmp[OCPATHMAX+1];
        int stat;
	pid_t pid = getpid();
	snprintf(tmp,sizeof(tmp)-1,"%s/%s.%ld/",ocglobalstate.tempdir,OCDIR,(long)pid);
#ifdef _MSC_VER
	stat = mkdir(tmp);
#else
	stat = mkdir(tmp,S_IRUSR | S_IWUSR | S_IXUSR);
#endif
	if(stat != 0 && errno != EEXIST) {
	    fprintf(stderr,"Cannot create cookie directory\n");
	    goto fail;
	}
	errno = 0;
	/* Create the unique cookie file name */
	stat = ocmktmp(tmp,&state->curlflags.cookiejar);
	state->curlflags.createdflags |= COOKIECREATED;
	if(stat != OC_NOERR && errno != EEXIST) {
	    fprintf(stderr,"Cannot create cookie file\n");
	    goto fail;
	}
	errno = 0;
    }
    OCASSERT(state->curlflags.cookiejar != NULL);

    /* Make sure the cookie jar exists and can be read and written */
    {
	FILE* f = NULL;
	char* fname = state->curlflags.cookiejar;
	/* See if the file exists already */
        f = fopen(fname,"r");
	if(f == NULL) {
	    /* Ok, create it */
	    f = fopen(fname,"w+");
	    if(f == NULL) {
	        fprintf(stderr,"Cookie file cannot be read and written: %s\n",fname);
	        {stat = OC_EPERM; goto fail;}
	    }
	} else { /* test if file can be written */
	    fclose(f);
	    f = fopen(fname,"r+");
	    if(f == NULL) {
	        fprintf(stderr,"Cookie file is cannot be written: %s\n",fname);
	        {stat = OC_EPERM; goto fail;}
	    }
	}
	if(f != NULL) fclose(f);
    }

#if 0
    /* Create a netrc file if specified  and required,
       where required => >1 NETRC triples exist */
    if(ocrc_netrc_required(state)) {
	/* WARNING: it appears that a user+pwd was specified specifically, then
           the netrc file will be completely disabled. */
	if(state->creds.userpwd != NULL) {
  	    oclog(OCLOGWARN,"The rc file specifies both netrc and user+pwd; this will cause curl to ignore the netrc file");
	}
	stat = oc_build_netrc(state);
    }
#endif

    return stat;

fail:
    return OCTHROW(stat);
}
Exemple #12
0
int
ocinternalinitialize(void)
{
    int stat = OC_NOERR;

    if(!ocglobalstate.initialized) {
        memset((void*)&ocglobalstate,0,sizeof(ocglobalstate));
	ocglobalstate.initialized = 1;
    }

    /* Capture $HOME */
    {
	char* p;
	char* q;
        char* home = getenv("HOME");
	char cwd[4096];
        if(ocglobalstate.home == NULL) {
#if defined(_WIN32) || defined(_WIN64)
	    home = getenv("TEMP");
#else
	    home = "/tmp";
#endif
	}
        if(home == NULL) {
	    home = getcwd(cwd,sizeof(cwd));
	    if(home == NULL || *home == '\0') home = ".";
	}

        /* Convert '\' to '/' */
        ocglobalstate.home = (char*)malloc(strlen(home) + 1);
	for(p=home,q=ocglobalstate.home;*p;p++,q++) {
	    if(*p == '\\') {*q = '/'; } else {*q = *p;}
	}
	*q = '\0';
    }

    /* Compute some xdr related flags */
    xxdr_init();

    ocloginit();

    oc_curl_protocols(&ocglobalstate); /* see what protocols are supported */

    /* compile the .dodsrc, if any */
    {
        char* path = NULL;
	char** alias;
	FILE* f = NULL;
        /* locate the configuration files: . first in '.',  then $HOME */
	for(alias=rcfilenames;*alias;alias++) {
	    size_t pathlen = strlen("./")+strlen(*alias)+1;
            path = (char*)malloc(pathlen);
	    if(path == NULL) return OC_ENOMEM;
	    if(!occopycat(path,pathlen,2,"./",*alias)) {
	        if(path) free(path);
		return OC_EOVERRUN;
	    }
  	    /* see if file is readable */
	    f = fopen(path,"r");
	    if(f != NULL) break;
    	    if(path != NULL) {free(path); path = NULL;} /* cleanup */
	}
	if(f == NULL) { /* try $HOME */
	    OCASSERT(path == NULL);
	    for(alias=rcfilenames;*alias;alias++) {
		size_t pathlen = strlen(ocglobalstate.home)+1+strlen(*alias)+1;
	        path = (char*)malloc(pathlen);
	        if(path == NULL) return OC_ENOMEM;
		if(!occopycat(path,pathlen,3,ocglobalstate.home,"/",*alias)) {
		    if(path) free(path);
		    return OC_EOVERRUN;
		}
		f = fopen(path,"r");
		if(f != NULL) break;
 	        if(path != NULL) {free(path); path=NULL;}
            }
	}
        if(f == NULL) {
            oclog(OCLOGDBG,"Cannot find runtime configuration file");
	} else {
	    OCASSERT(path != NULL);
       	    fclose(f);
            if(ocdebug > 1)
		fprintf(stderr, "DODS RC file: %s\n", path);
            if(ocdodsrc_read(*alias,path) == 0)
	        oclog(OCLOGERR, "Error parsing %s\n",path);
        }
        if(path != NULL) free(path);
    }

    return OCTHROW(stat);
}
Exemple #13
0
/*
    Set curl properties for link based on rc files etc.
*/
static int
ocsetcurlproperties(OCstate* state)
{
    CURLcode cstat = CURLE_OK;

    /* process the triple store wrt to this state */
    if(ocdodsrc_process(state) != OC_NOERR) {
	oclog(OCLOGERR,"Malformed .opendaprc configuration file");
	goto fail;
    }
    if(state->creds.username == NULL && state->creds.password == NULL) {
        if(state->uri->user != NULL && state->uri->password != NULL) {
	    /* this overrides .dodsrc */
            if(state->creds.password) free(state->creds.password);
            state->creds.password = nulldup(state->uri->password);
            if(state->creds.username) free(state->creds.username);
            state->creds.username = nulldup(state->uri->user);
	}
    }
    if(state->curlflags.useragent == NULL) {
        size_t len = strlen(DFALTUSERAGENT) + strlen(VERSION) + 1;
	char* agent = (char*)malloc(len+1);
	if(occopycat(agent,len,2,DFALTUSERAGENT,VERSION))
	    state->curlflags.useragent = agent;
	else
	    free(agent);
    }

    /* Some servers (e.g. thredds and columbia) appear to require a place
       to put cookies in order for some security functions to work
    */
    if(state->curlflags.cookiejar == NULL
       || *state->curlflags.cookiejar) {
#if 1
	/* Apparently anything non-null will work */
	state->curlflags.cookiejar = strdup("");
#else
	/* If no cookie file was defined, define a default */
	char* tmp;
	int fd;
        int stat;

        tmp = (char*)malloc(strlen(ocglobalstate.home)
				  +strlen("/")
				  +strlen(OCDIR)
				  +strlen("/")
				  +1);
	if(tmp == NULL)
	    return OC_ENOMEM;
	strcpy(tmp,ocglobalstate.home);
	strcat(tmp,"/");
	strcat(tmp,OCDIR);
	strcat(tmp,"/");
	stat = mkdir(tmp,S_IRUSR | S_IWUSR | S_IXUSR);
	if(stat != 0 && errno != EEXIST) {
	    fprintf(stderr,"Cannot create cookie file\n");
	    return stat;
	}
	errno = 0;
	/* Create the actual cookie file */
	stat = ocmktmp(tmp,&state->curlflags.cookiejar,&fd);
	close(fd);

#if 0
	fd = creat(tmp,S_IRUSR | S_IWUSR);
	if(fd < 0) {
	    fprintf(stderr,"Cannot create cookie file\n");
	    return OC_EPERM;
	}else
	    close(fd);
#endif
#endif
    }
    return OC_NOERR;

fail:
    if(cstat != CURLE_OK)
	oclog(OCLOGERR, "curl error: %s", curl_easy_strerror(cstat));
    return OC_ECURL;
}
Exemple #14
0
int
ocinternalinitialize(void)
{
    int stat = OC_NOERR;

    if(!ocglobalstate.initialized) {
        memset((void*)&ocglobalstate,0,sizeof(ocglobalstate));
	ocglobalstate.initialized = 1;
    }

    /* Compute some xdr related flags */
    xxdr_init();

    ocloginit();

    oc_curl_protocols(&ocglobalstate); /* see what protocols are supported */

    /* compile the .dodsrc, if any */
    {
        char* path = NULL;
        char* homepath = NULL;
	char** alias;
	FILE* f = NULL;
        /* locate the configuration files: . first in '.',  then $HOME */
	for(alias=rcfilenames;*alias;alias++) {
	    size_t pathlen = strlen("./")+strlen(*alias)+1;
            path = (char*)malloc(pathlen);
	    if(path == NULL) return OC_ENOMEM;
	    if(!occopycat(path,pathlen,2,"./",*alias)) {
	      if(path) free(path);
	      return OC_EOVERRUN;
	    }
  	    /* see if file is readable */
	    f = fopen(path,"r");
	    if(f != NULL) break;
    	    if(path != NULL) {free(path); path = NULL;} /* cleanup */
	}
	if(f == NULL) { /* try $HOME */
	    OCASSERT(path == NULL);
            homepath = getenv("HOME");
            if (homepath!= NULL) {
	        for(alias=rcfilenames;*alias;alias++) {
	            size_t pathlen = strlen(homepath)+1+strlen(*alias)+1;
	            path = (char*)malloc(pathlen);
	            if(path == NULL) return OC_ENOMEM;
		    if(!occopycat(path,pathlen,3,homepath,"/",*alias)) {
		      if(path) {free(path);}
		      return OC_EOVERRUN;
		    }
		    f = fopen(path,"r");
		    if(f != NULL) break;
 	            if(path != NULL) {free(path); path=NULL;}
		}
            }
	}
        if(f == NULL) {
            oclog(OCLOGDBG,"Cannot find runtime configuration file");
	} else {
	    OCASSERT(path != NULL);
       	    fclose(f);
            if(ocdebug > 1)
		fprintf(stderr, "DODS RC file: %s\n", path);
            if(ocdodsrc_read(*alias,path) == 0)
	        oclog(OCLOGERR, "Error parsing %s\n",path);
        }
        if(path != NULL) free(path);
    }
    return OCTHROW(stat);
}