// FileRev.cpp: implementation of the FileRev class.
//
//////////////////////////////////////////////////////////////////////

#include "extdll.h" 
#include "util.h"
#include "cbase.h" 



#include <clientapi.h>
#include "filehead.h"
#include "clientloguser.h"
#include "changesorter.h"
#include "filelogcache.h"

//////////////////////////////////////////////////////////////////////
// Construction/Destruction
//////////////////////////////////////////////////////////////////////

FileRev::FileRev(StrBuf newrev, FileHead* parent, StrBuf newchange, RevType revtype, bool text)
{
	rev = newrev;
	change = newchange;
	fh = parent;
	type = revtype;
	prev = NULL;
	next = NULL;
	fromcheck = false;
	intocheck = false;
	ent = NULL;
	istext = text;

	fromarrows = NULL;
	fromtexts = NULL;
	intotexts = NULL;
}

void FileRev::AddFromArrow(FileRev* rev, ArrowType atype)
{
	/* Do a quick check to avoid duplicates. */
	FileRevArrow* scan = fromarrows;
	while (scan)
	{
		if (scan->ptr == rev) return; //already got it!
		scan = scan->next;
	}

	fh->flc->numarrows++;

	if (
		(type == EDIT || type == ADD) 
		&& (atype != edit) ) atype = impure; //sanity check for "impure" integs
	FileRevArrow* newarrow = new FileRevArrow;
	newarrow->ptr = rev;
	newarrow->type = atype;
	switch (atype)
	{
	case edit: 
	case branch:
	case copy:
		newarrow->contrib = all; break;
	case ignore:
		newarrow->contrib = none; break;
	case impure:
	case merge:
		newarrow->contrib = some; break;
	}
	newarrow->next = fromarrows;
	fromarrows = newarrow;

	/* Downgrade "contrib" of other arrows as needed. */

	scan = fromarrows->next;
	while (scan)
	{
		switch (fromarrows->contrib)
		{
		case all:
			scan->contrib = none; break;
		case some:
			if (scan->contrib == all) scan->contrib = some; break;
		}
		scan = scan->next;
	}
}

void FileRev::AddFromText(StrBuf& infile, StrBuf& inrev, ArrowType atype)
{
	FileTextArrow* newtext = new FileTextArrow;
	newtext->file.Set(infile);
	newtext->rev.Set(inrev);
	newtext->type = atype;
	newtext->next = fromtexts;
	fromtexts = newtext;
}

void FileRev::AddIntoText(StrBuf& infile, StrBuf& inrev, ArrowType atype)
{
	FileTextArrow* newtext = new FileTextArrow;
	newtext->file.Set(infile);
	newtext->rev.Set(inrev);
	newtext->type = atype;
	newtext->next = intotexts;
	intotexts = newtext;
}

FileRev::~FileRev()
{
	FileRevArrow* rmg;
	while (fromarrows)
	{
		rmg = fromarrows->next;
		delete fromarrows;
		fromarrows = rmg;
	}

	if (next != NULL) delete next;
}
