DataMuseum.dk

Presents historical artifacts from the history of:

DKUUG/EUUG Conference tapes

This is an automatic "excavation" of a thematic subset of
artifacts from Datamuseum.dk's BitArchive.

See our Wiki for more about DKUUG/EUUG Conference tapes

Excavated with: AutoArchaeologist - Free & Open Source Software.


top - metrics - download
Index: T u

⟦19178a640⟧ TextFile

    Length: 8962 (0x2302)
    Types: TextFile
    Names: »update.c«

Derivation

└─⟦3d0c2be1b⟧ Bits:30001254 ISODE-5.0 Tape
    └─⟦eba4602b1⟧ »./isode-5.0.tar.Z« 
        └─⟦d3ac74d73⟧ 
            └─⟦this⟧ »isode-5.0/quipu/update.c« 

TextFile

/* update.c - write EDB back to disk after modify */

#ifndef lint
static char *rcsid = "$Header: /f/osi/quipu/RCS/update.c,v 6.0 89/03/18 23:42:00 mrose Rel $";
#endif

/*
 * $Header: /f/osi/quipu/RCS/update.c,v 6.0 89/03/18 23:42:00 mrose Rel $
 *
 *
 * $Log:	update.c,v $
 * Revision 6.0  89/03/18  23:42:00  mrose
 * Release 5.0
 * 
 */

/*
 *                                NOTICE
 *
 *    Acquisition, use, and distribution of this module and related
 *    materials are subject to the restrictions of a license agreement.
 *    Consult the Preface in the User's Manual for the full terms of
 *    this agreement.
 *
 */


#include "quipu/util.h"
#include "quipu/entry.h"
#include "tailor.h"
#include "quipu/read.h"
#include "quipu/dua.h"
#include "quipu/connection.h"

#ifndef NO_STATS
extern LLog * log_stat;
#endif
extern int dn_print ();

extern LLog * log_dsap;
extern char remote_lookup;

/* routine name is historic - not significant */

journal (myentry)
Entry myentry;
{
PS ps,entryps;
char filename [LINESIZE];
char savefile [LINESIZE];
DN dn;
FILE * fptr;
extern char * treedir;
extern char * parse_file;
Entry liststart;
int um;

	if (myentry == NULLENTRY) {
		LLOG (log_dsap,LLOG_FATAL,("update edb problem"));
		return NOTOK;
	}

	if ((ps = ps_alloc (str_open)) == NULLPS)
		return (NOTOK);

	if (str_setup (ps,filename,LINESIZE,1) == NOTOK)
		return (NOTOK);

	if ((myentry->e_parent != NULLENTRY) && (myentry->e_parent->e_leaf)) {
		liststart = myentry;
		if ((dn = get_copy_dn (liststart->e_parent)) == NULLDN) {
			/* there must be a root directory ! */
			LLOG (log_dsap,LLOG_EXCEPTIONS,("serious journal error"));
			return (NOTOK);
		} else {
			ps_printf (ps,"%s/",isodefile(treedir));
			dn_print (ps,dn,DIROUT);
			*ps->ps_ptr = 0;
			if ( mkdir (filename,0700) != 0 ) {
				LLOG (log_dsap,LLOG_EXCEPTIONS,("journal mkdir failure"));
				return (NOTOK);
			}
			ps_print (ps,"/EDB");
			*ps->ps_ptr = 0;
		}
		myentry->e_parent->e_leaf = FALSE;  /* not a leaf now !! */
	} else {
		if (myentry->e_parent == NULLENTRY) {
			liststart = myentry;
			ps_printf (ps,"%s/EDB",isodefile(treedir));
		} else {
			liststart = myentry->e_parent->e_child;
	 		if ((dn = get_copy_dn (liststart->e_parent)) == NULLDN)
				ps_printf (ps,"%s/EDB",isodefile(treedir));
			else {
				ps_printf (ps,"%s/",isodefile(treedir));
				dn_print (ps,dn,DIROUT);
				ps_print (ps,"/EDB");
			}
		}
		*ps->ps_ptr = 0;

		(void) strcpy (savefile,filename);
		(void) strcat (savefile,".bak");

		if (rename (filename,savefile) != OK) {
			LLOG (log_dsap,LLOG_EXCEPTIONS,("rename %s, %s failed",filename,savefile));
			return NOTOK;
		}

	}

	um = umask (0177);
	if ((fptr = fopen (filename,"w")) == (FILE *) NULL) {
		LLOG (log_dsap,LLOG_EXCEPTIONS,("file_open failed"));
		return NOTOK;
		}
	(void) umask (um);

	if ((entryps = ps_alloc (std_open)) == NULLPS) {
		LLOG (log_dsap,LLOG_EXCEPTIONS,("ps_alloc failed"));
		return NOTOK;
	}
	if (std_setup (entryps,fptr) == NOTOK) {
		LLOG (log_dsap,LLOG_EXCEPTIONS,("std_setup failed"));
		return NOTOK;
	}

	parse_file = filename;
	header_print (entryps,liststart,EDBOUT);

	entry_block_print (entryps,liststart,EDBOUT);
	ps_free (entryps);
	ps_free (ps);
	(void) fclose (fptr);
	sync ();

	return (OK);

}

Entry find_sibling (object,start)
RDN object;
Entry start;
{
	if (start == NULLENTRY) 
		return (NULLENTRY);

	while (rdn_cmp (start->e_name, object) != OK) {
		start = start->e_sibling ;
		if ( start == NULLENTRY ) 
			return (NULLENTRY);
	}
	return (start);
}

Entry read_edb (version,dn,from)
char ** version;
DN dn,from;
{
struct DSError error;
static struct ds_bind_arg bindarg;
static struct ds_bind_arg bindresult;
static struct ds_bind_error binderr;
struct PSAPaddr * addr, * get_dsa_psap();
int ad;
struct getedb_arg arg;
struct getedb_result result;

	/* read from of remote DSA */
	/* Do synchronus read for now */
	/* Async read eventually */

	make_dsa_bind_arg (&bindarg);

	if ((addr = get_dsa_psap (from)) == NULLPA) {
		LLOG (log_dsap,LLOG_EXCEPTIONS,("get edb psap lookup failed"));
		return (NULLENTRY);
	}
	
	if (dap_bind (&ad, &bindarg, &binderr, &bindresult,addr) != OK) {
		LLOG (log_dsap,LLOG_EXCEPTIONS,("get edb bind failed"));
		return (NULLENTRY);
	}

	arg.ga_entry = dn;
	arg.ga_version = *version;
	DLOG(log_dsap, LLOG_NOTICE, ("EDBARG: ver = %s", arg.ga_version));

	if (getedb (&arg,&error,&result,ad) != OK) {
		LLOG (log_dsap,LLOG_EXCEPTIONS,("getedb remote operation failed"));
		log_ds_error (&error);
		ds_error_free (&error);
		return (NULLENTRY);
	}

	(void) dap_unbind (ad);

	*version = result.gr_version;
	if (result.gr_version == NULLCP)
		LLOG(log_dsap, LLOG_NOTICE, ("EDBRES: NULL version"));
	else 
		DLOG(log_dsap, LLOG_NOTICE, ("EDBRES: ver = %s", result.gr_version));

	return (result.gr_edb);
}

slave_update ()
{
Entry my_entry;
extern DN mydsadn;
struct edb_info * dsainfo;
Entry new_entry, eptr, old_entry, temp, sibl;
struct DSError  error;
static char *version = NULLCP;
AV_Sequence avs;

	DLOG (log_dsap,LLOG_TRACE,("slave update"));

	if ((my_entry = local_find_entry (mydsadn,TRUE)) == NULLENTRY)
		fatal (82,"Can't update slaves - my entry has gone");

	for (avs = my_entry->e_dsainfo->dsa_attr ; avs != NULLAV; avs=avs->avseq_next) {
		if (avs->avseq_av == NULLAttrV)
			continue;
		dsainfo = avs->avseq_av->av_un.av_update;
		if (dsainfo->edb_getfrom == NULLDN)
			continue;  /* not an EDB to update */

		if ((eptr = local_find_entry (dsainfo->edb_name,FALSE)) == NULLENTRY) {
			pslog (log_dsap,LLOG_NOTICE,"local slave missing",dn_print,(caddr_t)dsainfo->edb_name);
			continue;
		} else
			version = eptr->e_edbversion;

		if ((new_entry = read_edb (&version,dsainfo->edb_name,dsainfo->edb_getfrom)) == NULLENTRY) {
			LLOG (log_dsap,LLOG_NOTICE,("getedb: EDB's are the same!"));
			continue;
		}
		if (version == NULLCP)
			eptr->e_edbversion = "Unknown";
		else
			eptr->e_edbversion = strdup (version);

		for (temp = new_entry; temp != NULLENTRY; temp=temp->e_sibling) {
			temp->e_parent = eptr;
			if (unravel_attribute (temp,&error,TRUE) != OK) {
				log_ds_error (&error);
				fatal (-44,"new edb won't unravel");
			}

			if ((old_entry = find_sibling (temp->e_name,eptr->e_child)) != NULLENTRY) {
				temp->e_leaf = FALSE;
				temp->e_allchildrenpresent = old_entry->e_allchildrenpresent;
				temp->e_child = old_entry->e_child;
				for (sibl = temp->e_child; sibl != NULLENTRY; sibl=sibl->e_sibling)
					sibl->e_parent = temp;
				if (old_entry->e_edbversion != NULLCP)
					temp->e_edbversion = strdup (old_entry->e_edbversion);
			}

		}
		for (temp = eptr->e_child; temp != NULLENTRY; temp=temp->e_sibling) 
			entry_free (temp);

		eptr->e_child = new_entry;
		if (journal (new_entry) != OK)
			fatal (-45,"Lost old EDB, can't write new one !!!");
#ifndef NO_STATS
		else 
			pslog (log_stat,LLOG_NOTICE,"slave update",dn_print,(caddr_t)dsainfo->edb_name);
#endif
		if ((my_entry = local_find_entry (mydsadn,TRUE)) == NULLENTRY)
			fatal (-80,"My entry has disappeared");
	}

}


do_get_edb (arg,error,result,binddn)
struct getedb_arg *arg;
struct DSError	  *error;
struct getedb_result *result;
DN binddn;
{
Entry eptr;
extern DN mydsadn;
Entry my_entry;
AV_Sequence avs;
struct edb_info * dsainfo;
char proceed = FALSE;
struct dn_seq *dnseq;

	dn_decode (arg->ga_entry);

#ifndef NO_STATS
	pslog (log_stat,LLOG_NOTICE,"getedb",dn_print,(caddr_t)arg->ga_entry);
#endif
	DLOG (log_dsap,LLOG_DEBUG,("getedb '%s'",arg->ga_version));

	remote_lookup = FALSE;
	if ((eptr = really_find_entry (arg->ga_entry,error,FALSE)) == NULLENTRY) {
		if (error->dse_type == DSE_REFERRAL) {
			error->dse_type = DSE_SERVICEERROR;
			error->ERR_SERVICE.DSE_sv_problem = DSE_SV_CHAININGREQUIRED;
			remote_lookup = TRUE;
			return (DS_ERROR_REMOTE);
		}
	}
	remote_lookup = TRUE;

	if (eptr->e_edbversion != NULLCP) {
		DLOG(log_dsap, LLOG_DEBUG, ("edb_ver = %s", eptr->e_edbversion));

		if (lexequ (arg->ga_version,eptr->e_edbversion) == 0) {
			result->gr_version = eptr->e_edbversion;
			result->gr_next = NULL_GETRESULT;
			result->gr_edb = NULLENTRY;
			return (DS_OK);
		}
	}

	if ((my_entry = local_find_entry (mydsadn,TRUE)) == NULLENTRY)
		fatal (84,"my entry has gone - no getedb");

	/* Check we will send to this DSA */
	for (avs = my_entry->e_dsainfo->dsa_attr ; avs != NULLAV; avs=avs->avseq_next) {
		if (avs->avseq_av == NULLAttrV)
			continue;
		dsainfo = avs->avseq_av->av_un.av_update;
		if (dn_cmp(dsainfo->edb_name,arg->ga_entry) == 0) {
			for (dnseq=dsainfo->edb_allowed; dnseq!=NULLDNSEQ; dnseq=dnseq->dns_next) {
				if (dn_cmp(dnseq->dns_dn,binddn) == 0) {
					proceed = TRUE;
					break;
				}
			}
		}
		if (proceed)
			break;
	}
					
	if (!proceed) {
		error->dse_type = DSE_SECURITYERROR;
		error->ERR_SECURITY.DSE_sc_problem = DSE_SC_ACCESSRIGHTS;
		return (DS_ERROR_REMOTE);
	}

	result->gr_version = eptr->e_edbversion;
	result->gr_edb = eptr->e_child;
	result->gr_next = NULL_GETRESULT;
	return (DS_OK);
}