#
# Copyright (C) 2005 Fredrik Kuivinen
#

import sys, re, os, traceback
from sets import Set

def die(*args):
    printList(args, sys.stderr)
    sys.exit(2)

def printList(list, file=sys.stdout):
    for x in list:
        file.write(str(x))
        file.write(' ')
    file.write('\n')

import subprocess

# Debugging machinery
# -------------------

DEBUG = 0
functionsToDebug = Set()

def addDebug(func):
    if type(func) == str:
        functionsToDebug.add(func)
    else:
        functionsToDebug.add(func.func_name)

def debug(*args):
    if DEBUG:
        funcName = traceback.extract_stack()[-2][2]
        if funcName in functionsToDebug:
            printList(args)

# Program execution
# -----------------

class ProgramError(Exception):
    def __init__(self, progStr, error):
        self.progStr = progStr
        self.error = error

    def __str__(self):
        return self.progStr + ': ' + self.error

addDebug('runProgram')
def runProgram(prog, input=None, returnCode=False, env=None, pipeOutput=True):
    debug('runProgram prog:', str(prog), 'input:', str(input))
    if type(prog) is str:
        progStr = prog
    else:
        progStr = ' '.join(prog)
    
    try:
        if pipeOutput:
            stderr = subprocess.STDOUT
            stdout = subprocess.PIPE
        else:
            stderr = None
            stdout = None
        pop = subprocess.Popen(prog,
                               shell = type(prog) is str,
                               stderr=stderr,
                               stdout=stdout,
                               stdin=subprocess.PIPE,
                               env=env)
    except OSError, e:
        debug('strerror:', e.strerror)
        raise ProgramError(progStr, e.strerror)

    if input != None:
        pop.stdin.write(input)
    pop.stdin.close()

    if pipeOutput:
        out = pop.stdout.read()
    else:
        out = ''

    code = pop.wait()
    if returnCode:
        ret = [out, code]
    else:
        ret = out
    if code != 0 and not returnCode:
        debug('error output:', out)
        debug('prog:', prog)
        raise ProgramError(progStr, out)
#    debug('output:', out.replace('\0', '\n'))
    return ret

# Code for computing common ancestors
# -----------------------------------

currentId = 0
def getUniqueId():
    global currentId
    currentId += 1
    return currentId

# The 'virtual' commit objects have SHAs which are integers
shaRE = re.compile('^[0-9a-f]{40}$')
def isSha(obj):
    return (type(obj) is str and bool(shaRE.match(obj))) or \
           (type(obj) is int and obj >= 1)

class Commit:
    def __init__(self, sha, parents, tree=None):
        self.parents = parents
        self.firstLineMsg = None
        self.children = []

        if tree:
            tree = tree.rstrip()
            assert(isSha(tree))
        self._tree = tree

        if not sha:
            self.sha = getUniqueId()
            self.virtual = True
            self.firstLineMsg = 'virtual commit'
            assert(isSha(tree))
        else:
            self.virtual = False
            self.sha = sha.rstrip()
        assert(isSha(self.sha))

    def tree(self):
        self.getInfo()
        assert(self._tree != None)
        return self._tree

    def shortInfo(self):
        self.getInfo()
        return str(self.sha) + ' ' + self.firstLineMsg

    def __str__(self):
        return self.shortInfo()

    def getInfo(self):
        if self.virtual or self.firstLineMsg != None:
            return
        else:
            info = runProgram(['git-cat-file', 'commit', self.sha])
            info = info.split('\n')
            msg = False
            for l in info:
                if msg:
                    self.firstLineMsg = l
                    break
                else:
                    if l.startswith('tree'):
                        self._tree = l[5:].rstrip()
                    elif l == '':
                        msg = True

class Graph:
    def __init__(self):
        self.commits = []
        self.shaMap = {}

    def addNode(self, node):
        assert(isinstance(node, Commit))
        self.shaMap[node.sha] = node
        self.commits.append(node)
        for p in node.parents:
            p.children.append(node)
        return node

    def reachableNodes(self, n1, n2):
        res = {}
        def traverse(n):
            res[n] = True
            for p in n.parents:
                traverse(p)

        traverse(n1)
        traverse(n2)
        return res

    def fixParents(self, node):
        for x in range(0, len(node.parents)):
            node.parents[x] = self.shaMap[node.parents[x]]

# addDebug('buildGraph')
def buildGraph(heads):
    debug('buildGraph heads:', heads)
    for h in heads:
        assert(isSha(h))

    g = Graph()

    out = runProgram(['git-rev-list', '--parents'] + heads)
    for l in out.split('\n'):
        if l == '':
            continue
        shas = l.split(' ')

        # This is a hack, we temporarily use the 'parents' attribute
        # to contain a list of SHA1:s. They are later replaced by proper
        # Commit objects.
        c = Commit(shas[0], shas[1:])

        g.commits.append(c)
        g.shaMap[c.sha] = c

    for c in g.commits:
        g.fixParents(c)

    for c in g.commits:
        for p in c.parents:
            p.children.append(c)
    return g

# Write the empty tree to the object database and return its SHA1
def writeEmptyTree():
    tmpIndex = os.environ.get('GIT_DIR', '.git') + '/merge-tmp-index'
    def delTmpIndex():
        try:
            os.unlink(tmpIndex)
        except OSError:
            pass
    delTmpIndex()
    newEnv = os.environ.copy()
    newEnv['GIT_INDEX_FILE'] = tmpIndex
    res = runProgram(['git-write-tree'], env=newEnv).rstrip()
    delTmpIndex()
    return res

def addCommonRoot(graph):
    roots = []
    for c in graph.commits:
        if len(c.parents) == 0:
            roots.append(c)

    superRoot = Commit(sha=None, parents=[], tree=writeEmptyTree())
    graph.addNode(superRoot)
    for r in roots:
        r.parents = [superRoot]
    superRoot.children = roots
    return superRoot

def getCommonAncestors(graph, commit1, commit2):
    '''Find the common ancestors for commit1 and commit2'''
    assert(isinstance(commit1, Commit) and isinstance(commit2, Commit))

    def traverse(start, set):
        stack = [start]
        while len(stack) > 0:
            el = stack.pop()
            set.add(el)
            for p in el.parents:
                if p not in set:
                    stack.append(p)
    h1Set = Set()
    h2Set = Set()
    traverse(commit1, h1Set)
    traverse(commit2, h2Set)
    shared = h1Set.intersection(h2Set)

    if len(shared) == 0:
        shared = [addCommonRoot(graph)]
        
    res = Set()

    for s in shared:
        if len([c for c in s.children if c in shared]) == 0:
            res.add(s)
    return list(res)
