Imported Upstream version 6.10.0.49

Former-commit-id: 1d6753294b2993e1fbf92de9366bb9544db4189b
This commit is contained in:
Xamarin Public Jenkins (auto-signing)
2020-01-16 16:38:04 +00:00
parent d94e79959b
commit 468663ddbb
48518 changed files with 2789335 additions and 61176 deletions

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,276 @@
"""Utilities for enumeration of finite and countably infinite sets.
"""
###
# Countable iteration
# Simplifies some calculations
class Aleph0(int):
_singleton = None
def __new__(type):
if type._singleton is None:
type._singleton = int.__new__(type)
return type._singleton
def __repr__(self): return '<aleph0>'
def __str__(self): return 'inf'
def __cmp__(self, b):
return 1
def __sub__(self, b):
raise ValueError,"Cannot subtract aleph0"
__rsub__ = __sub__
def __add__(self, b):
return self
__radd__ = __add__
def __mul__(self, b):
if b == 0: return b
return self
__rmul__ = __mul__
def __floordiv__(self, b):
if b == 0: raise ZeroDivisionError
return self
__rfloordiv__ = __floordiv__
__truediv__ = __floordiv__
__rtuediv__ = __floordiv__
__div__ = __floordiv__
__rdiv__ = __floordiv__
def __pow__(self, b):
if b == 0: return 1
return self
aleph0 = Aleph0()
def base(line):
return line*(line+1)//2
def pairToN((x,y)):
line,index = x+y,y
return base(line)+index
def getNthPairInfo(N):
# Avoid various singularities
if N==0:
return (0,0)
# Gallop to find bounds for line
line = 1
next = 2
while base(next)<=N:
line = next
next = line << 1
# Binary search for starting line
lo = line
hi = line<<1
while lo + 1 != hi:
#assert base(lo) <= N < base(hi)
mid = (lo + hi)>>1
if base(mid)<=N:
lo = mid
else:
hi = mid
line = lo
return line, N - base(line)
def getNthPair(N):
line,index = getNthPairInfo(N)
return (line - index, index)
def getNthPairBounded(N,W=aleph0,H=aleph0,useDivmod=False):
"""getNthPairBounded(N, W, H) -> (x, y)
Return the N-th pair such that 0 <= x < W and 0 <= y < H."""
if W <= 0 or H <= 0:
raise ValueError,"Invalid bounds"
elif N >= W*H:
raise ValueError,"Invalid input (out of bounds)"
# Simple case...
if W is aleph0 and H is aleph0:
return getNthPair(N)
# Otherwise simplify by assuming W < H
if H < W:
x,y = getNthPairBounded(N,H,W,useDivmod=useDivmod)
return y,x
if useDivmod:
return N%W,N//W
else:
# Conceptually we want to slide a diagonal line across a
# rectangle. This gives more interesting results for large
# bounds than using divmod.
# If in lower left, just return as usual
cornerSize = base(W)
if N < cornerSize:
return getNthPair(N)
# Otherwise if in upper right, subtract from corner
if H is not aleph0:
M = W*H - N - 1
if M < cornerSize:
x,y = getNthPair(M)
return (W-1-x,H-1-y)
# Otherwise, compile line and index from number of times we
# wrap.
N = N - cornerSize
index,offset = N%W,N//W
# p = (W-1, 1+offset) + (-1,1)*index
return (W-1-index, 1+offset+index)
def getNthPairBoundedChecked(N,W=aleph0,H=aleph0,useDivmod=False,GNP=getNthPairBounded):
x,y = GNP(N,W,H,useDivmod)
assert 0 <= x < W and 0 <= y < H
return x,y
def getNthNTuple(N, W, H=aleph0, useLeftToRight=False):
"""getNthNTuple(N, W, H) -> (x_0, x_1, ..., x_W)
Return the N-th W-tuple, where for 0 <= x_i < H."""
if useLeftToRight:
elts = [None]*W
for i in range(W):
elts[i],N = getNthPairBounded(N, H)
return tuple(elts)
else:
if W==0:
return ()
elif W==1:
return (N,)
elif W==2:
return getNthPairBounded(N, H, H)
else:
LW,RW = W//2, W - (W//2)
L,R = getNthPairBounded(N, H**LW, H**RW)
return (getNthNTuple(L,LW,H=H,useLeftToRight=useLeftToRight) +
getNthNTuple(R,RW,H=H,useLeftToRight=useLeftToRight))
def getNthNTupleChecked(N, W, H=aleph0, useLeftToRight=False, GNT=getNthNTuple):
t = GNT(N,W,H,useLeftToRight)
assert len(t) == W
for i in t:
assert i < H
return t
def getNthTuple(N, maxSize=aleph0, maxElement=aleph0, useDivmod=False, useLeftToRight=False):
"""getNthTuple(N, maxSize, maxElement) -> x
Return the N-th tuple where len(x) < maxSize and for y in x, 0 <=
y < maxElement."""
# All zero sized tuples are isomorphic, don't ya know.
if N == 0:
return ()
N -= 1
if maxElement is not aleph0:
if maxSize is aleph0:
raise NotImplementedError,'Max element size without max size unhandled'
bounds = [maxElement**i for i in range(1, maxSize+1)]
S,M = getNthPairVariableBounds(N, bounds)
else:
S,M = getNthPairBounded(N, maxSize, useDivmod=useDivmod)
return getNthNTuple(M, S+1, maxElement, useLeftToRight=useLeftToRight)
def getNthTupleChecked(N, maxSize=aleph0, maxElement=aleph0,
useDivmod=False, useLeftToRight=False, GNT=getNthTuple):
# FIXME: maxsize is inclusive
t = GNT(N,maxSize,maxElement,useDivmod,useLeftToRight)
assert len(t) <= maxSize
for i in t:
assert i < maxElement
return t
def getNthPairVariableBounds(N, bounds):
"""getNthPairVariableBounds(N, bounds) -> (x, y)
Given a finite list of bounds (which may be finite or aleph0),
return the N-th pair such that 0 <= x < len(bounds) and 0 <= y <
bounds[x]."""
if not bounds:
raise ValueError,"Invalid bounds"
if not (0 <= N < sum(bounds)):
raise ValueError,"Invalid input (out of bounds)"
level = 0
active = range(len(bounds))
active.sort(key=lambda i: bounds[i])
prevLevel = 0
for i,index in enumerate(active):
level = bounds[index]
W = len(active) - i
if level is aleph0:
H = aleph0
else:
H = level - prevLevel
levelSize = W*H
if N<levelSize: # Found the level
idelta,delta = getNthPairBounded(N, W, H)
return active[i+idelta],prevLevel+delta
else:
N -= levelSize
prevLevel = level
else:
raise RuntimError,"Unexpected loop completion"
def getNthPairVariableBoundsChecked(N, bounds, GNVP=getNthPairVariableBounds):
x,y = GNVP(N,bounds)
assert 0 <= x < len(bounds) and 0 <= y < bounds[x]
return (x,y)
###
def testPairs():
W = 3
H = 6
a = [[' ' for x in range(10)] for y in range(10)]
b = [[' ' for x in range(10)] for y in range(10)]
for i in range(min(W*H,40)):
x,y = getNthPairBounded(i,W,H)
x2,y2 = getNthPairBounded(i,W,H,useDivmod=True)
print i,(x,y),(x2,y2)
a[y][x] = '%2d'%i
b[y2][x2] = '%2d'%i
print '-- a --'
for ln in a[::-1]:
if ''.join(ln).strip():
print ' '.join(ln)
print '-- b --'
for ln in b[::-1]:
if ''.join(ln).strip():
print ' '.join(ln)
def testPairsVB():
bounds = [2,2,4,aleph0,5,aleph0]
a = [[' ' for x in range(15)] for y in range(15)]
b = [[' ' for x in range(15)] for y in range(15)]
for i in range(min(sum(bounds),40)):
x,y = getNthPairVariableBounds(i, bounds)
print i,(x,y)
a[y][x] = '%2d'%i
print '-- a --'
for ln in a[::-1]:
if ''.join(ln).strip():
print ' '.join(ln)
###
# Toggle to use checked versions of enumeration routines.
if False:
getNthPairVariableBounds = getNthPairVariableBoundsChecked
getNthPairBounded = getNthPairBoundedChecked
getNthNTuple = getNthNTupleChecked
getNthTuple = getNthTupleChecked
if __name__ == '__main__':
testPairs()
testPairsVB()

View File

@@ -0,0 +1,170 @@
# -*- Makefile -*-
# Usage: make test.N.report
#
# COUNT can be over-ridden to change the number of tests generated per
# file, and TESTARGS is used to change the type generation. Make sure
# to 'make clean' after changing either of these parameters.
TESTARGS := --no-unsigned --no-vector --no-complex --no-bool
COUNT := 1
TIMEOUT := 5
CFLAGS := -std=gnu99
X_COMPILER := gcc
X_LL_CFLAGS := -emit-llvm -S
Y_COMPILER := clang
Y_LL_CFLAGS := -emit-llvm -S
CC := gcc
###
ABITESTGEN := ../ABITestGen.py
ifndef VERBOSE
Verb := @
endif
.PHONY: test.%.report
test.%.report: temps/test.%.xx.diff temps/test.%.xy.diff temps/test.%.yx.diff temps/test.%.yy.diff
@ok=1;\
for t in $^; do \
if [ -s $$t ]; then \
echo "TEST $*: $$t failed"; \
ok=0;\
fi; \
done; \
if [ $$ok -eq 1 ]; then \
true; \
else \
false; \
fi
.PHONY: test.%.defs-report
test.%.defs-report: temps/test.%.defs.diff
@for t in $^; do \
if [ -s $$t ]; then \
echo "TEST $*: $$t failed"; \
cat $$t; \
fi; \
done
.PHONY: test.%.build
test.%.build: temps/test.%.ref temps/test.%.xx temps/test.%.xy temps/test.%.yx temps/test.%.yy temps/test.%.x.defs temps/test.%.y.defs
@true
###
# Diffs and output
.PRECIOUS: temps/.dir
.PRECIOUS: temps/test.%.xx.diff
temps/test.%.xx.diff: temps/test.%.ref.out temps/test.%.xx.out
$(Verb) diff $^ > $@ || true
.PRECIOUS: temps/test.%.xy.diff
temps/test.%.xy.diff: temps/test.%.ref.out temps/test.%.xy.out
$(Verb) diff $^ > $@ || true
.PRECIOUS: temps/test.%.yx.diff
temps/test.%.yx.diff: temps/test.%.ref.out temps/test.%.yx.out
$(Verb) diff $^ > $@ || true
.PRECIOUS: temps/test.%.yy.diff
temps/test.%.yy.diff: temps/test.%.ref.out temps/test.%.yy.out
$(Verb) diff $^ > $@ || true
.PRECIOUS: temps/test.%.defs.diff
temps/test.%.defs.diff: temps/test.%.x.defs temps/test.%.y.defs
$(Verb) zipdifflines \
--replace "%struct.T[0-9]+" "%struct.s" \
--replace "%union.T[0-9]+" "%struct.s" \
--replace "byval align [0-9]+" "byval" \
$^ > $@
.PRECIOUS: temps/test.%.out
temps/test.%.out: temps/test.%
-$(Verb) ./$< > $@
# Executables
.PRECIOUS: temps/test.%.ref
temps/test.%.ref: temps/test.%.driver.ref.o temps/test.%.a.ref.o temps/test.%.b.ref.o
$(Verb) $(CC) $(CFLAGS) $(CC_CFLAGS) -O3 -o $@ $^
.PRECIOUS: temps/test.%.xx
temps/test.%.xx: temps/test.%.driver.ref.o temps/test.%.a.x.o temps/test.%.b.x.o
$(Verb) $(CC) $(CFLAGS) $(CC_CFLAGS) -O3 -o $@ $^
.PRECIOUS: temps/test.%.xy
temps/test.%.xy: temps/test.%.driver.ref.o temps/test.%.a.x.o temps/test.%.b.y.o
$(Verb) $(CC) $(CFLAGS) $(CC_CFLAGS) -O3 -o $@ $^
.PRECIOUS: temps/test.%.yx
temps/test.%.yx: temps/test.%.driver.ref.o temps/test.%.a.y.o temps/test.%.b.x.o
$(Verb) $(CC) $(CFLAGS) $(CC_CFLAGS) -O3 -o $@ $^
.PRECIOUS: temps/test.%.yy
temps/test.%.yy: temps/test.%.driver.ref.o temps/test.%.a.y.o temps/test.%.b.y.o
$(Verb) $(CC) $(CFLAGS) $(CC_CFLAGS) -O3 -o $@ $^
# Object files
.PRECIOUS: temps/test.%.ref.o
temps/test.%.ref.o: inputs/test.%.c temps/.dir
$(Verb) $(CC) -c $(CFLAGS) $(CC_CFLAGS) -o $@ $<
.PRECIOUS: temps/test.%.x.o
temps/test.%.x.o: inputs/test.%.c temps/.dir
$(Verb) $(X_COMPILER) -c $(CFLAGS) $(X_CFLAGS) -o $@ $<
.PRECIOUS: temps/test.%.y.o
temps/test.%.y.o: inputs/test.%.c temps/.dir
$(Verb) $(Y_COMPILER) -c $(CFLAGS) $(Y_CFLAGS) -o $@ $<
.PRECIOUS: temps/test.%.x.defs
temps/test.%.x.defs: temps/test.%.a.x.ll temps/.dir
-$(Verb) -grep '^define ' $< > $@
.PRECIOUS: temps/test.%.y.defs
temps/test.%.y.defs: temps/test.%.a.y.ll temps/.dir
-$(Verb) -grep '^define ' $< > $@
.PRECIOUS: temps/test.%.a.x.ll
temps/test.%.a.x.ll: inputs/test.%.a.c temps/.dir
$(Verb) $(X_COMPILER) $(CFLAGS) $(X_LL_CFLAGS) $(X_CFLAGS) -o $@ $<
.PRECIOUS: temps/test.%.b.x.ll
temps/test.%.b.x.ll: inputs/test.%.b.c temps/.dir
$(Verb) $(X_COMPILER) $(CFLAGS) $(X_LL_CFLAGS) $(X_CFLAGS) -o $@ $<
.PRECIOUS: temps/test.%.a.y.ll
temps/test.%.a.y.ll: inputs/test.%.a.c temps/.dir
$(Verb) $(Y_COMPILER) $(CFLAGS) $(Y_LL_CFLAGS) $(Y_CFLAGS) -o $@ $<
.PRECIOUS: temps/test.%.b.y.ll
temps/test.%.b.y.ll: inputs/test.%.b.c temps/.dir
$(Verb) $(Y_COMPILER) $(CFLAGS) $(Y_LL_CFLAGS) $(Y_CFLAGS) -o $@ $<
# Input generation
.PHONY: test.%.top
test.%.top: inputs/test.%.a.c inputs/test.%.b.c inputs/test.%.driver.c
@true
.PRECIOUS: inputs/test.%.a.c inputs/test.%.b.c inputs/test.%.driver.c
inputs/test.%.a.c: test.%.generate
@true
inputs/test.%.b.c: test.%.generate
@true
inputs/test.%.driver.c: test.%.generate
@true
.PHONY: test.%.generate
.PRECIOUS: inputs/.dir
test.%.generate: $(ABITESTGEN) inputs/.dir
$(Verb) $(ABITESTGEN) $(TESTARGS) -o inputs/test.$*.a.c -T inputs/test.$*.b.c -D inputs/test.$*.driver.c --min=$(shell expr $* '*' $(COUNT)) --count=$(COUNT)
# Cleaning
clean-temps:
$(Verb) rm -rf temps
clean:
$(Verb) rm -rf temps inputs
# Etc.
%/.dir:
$(Verb) mkdir -p $* > /dev/null
$(Verb) $(DATE) > $@

View File

@@ -0,0 +1,475 @@
"""Flexible enumeration of C types."""
from Enumeration import *
# TODO:
# - struct improvements (flexible arrays, packed &
# unpacked, alignment)
# - objective-c qualified id
# - anonymous / transparent unions
# - VLAs
# - block types
# - K&R functions
# - pass arguments of different types (test extension, transparent union)
# - varargs
###
# Actual type types
class Type:
def isBitField(self):
return False
def isPaddingBitField(self):
return False
def getTypeName(self, printer):
name = 'T%d' % len(printer.types)
typedef = self.getTypedefDef(name, printer)
printer.addDeclaration(typedef)
return name
class BuiltinType(Type):
def __init__(self, name, size, bitFieldSize=None):
self.name = name
self.size = size
self.bitFieldSize = bitFieldSize
def isBitField(self):
return self.bitFieldSize is not None
def isPaddingBitField(self):
return self.bitFieldSize is 0
def getBitFieldSize(self):
assert self.isBitField()
return self.bitFieldSize
def getTypeName(self, printer):
return self.name
def sizeof(self):
return self.size
def __str__(self):
return self.name
class EnumType(Type):
unique_id = 0
def __init__(self, index, enumerators):
self.index = index
self.enumerators = enumerators
self.unique_id = self.__class__.unique_id
self.__class__.unique_id += 1
def getEnumerators(self):
result = ''
for i, init in enumerate(self.enumerators):
if i > 0:
result = result + ', '
result = result + 'enum%dval%d_%d' % (self.index, i, self.unique_id)
if init:
result = result + ' = %s' % (init)
return result
def __str__(self):
return 'enum { %s }' % (self.getEnumerators())
def getTypedefDef(self, name, printer):
return 'typedef enum %s { %s } %s;'%(name, self.getEnumerators(), name)
class RecordType(Type):
def __init__(self, index, isUnion, fields):
self.index = index
self.isUnion = isUnion
self.fields = fields
self.name = None
def __str__(self):
def getField(t):
if t.isBitField():
return "%s : %d;" % (t, t.getBitFieldSize())
else:
return "%s;" % t
return '%s { %s }'%(('struct','union')[self.isUnion],
' '.join(map(getField, self.fields)))
def getTypedefDef(self, name, printer):
def getField((i, t)):
if t.isBitField():
if t.isPaddingBitField():
return '%s : 0;'%(printer.getTypeName(t),)
else:
return '%s field%d : %d;'%(printer.getTypeName(t),i,
t.getBitFieldSize())
else:
return '%s field%d;'%(printer.getTypeName(t),i)
fields = map(getField, enumerate(self.fields))
# Name the struct for more readable LLVM IR.
return 'typedef %s %s { %s } %s;'%(('struct','union')[self.isUnion],
name, ' '.join(fields), name)
class ArrayType(Type):
def __init__(self, index, isVector, elementType, size):
if isVector:
# Note that for vectors, this is the size in bytes.
assert size > 0
else:
assert size is None or size >= 0
self.index = index
self.isVector = isVector
self.elementType = elementType
self.size = size
if isVector:
eltSize = self.elementType.sizeof()
assert not (self.size % eltSize)
self.numElements = self.size // eltSize
else:
self.numElements = self.size
def __str__(self):
if self.isVector:
return 'vector (%s)[%d]'%(self.elementType,self.size)
elif self.size is not None:
return '(%s)[%d]'%(self.elementType,self.size)
else:
return '(%s)[]'%(self.elementType,)
def getTypedefDef(self, name, printer):
elementName = printer.getTypeName(self.elementType)
if self.isVector:
return 'typedef %s %s __attribute__ ((vector_size (%d)));'%(elementName,
name,
self.size)
else:
if self.size is None:
sizeStr = ''
else:
sizeStr = str(self.size)
return 'typedef %s %s[%s];'%(elementName, name, sizeStr)
class ComplexType(Type):
def __init__(self, index, elementType):
self.index = index
self.elementType = elementType
def __str__(self):
return '_Complex (%s)'%(self.elementType)
def getTypedefDef(self, name, printer):
return 'typedef _Complex %s %s;'%(printer.getTypeName(self.elementType), name)
class FunctionType(Type):
def __init__(self, index, returnType, argTypes):
self.index = index
self.returnType = returnType
self.argTypes = argTypes
def __str__(self):
if self.returnType is None:
rt = 'void'
else:
rt = str(self.returnType)
if not self.argTypes:
at = 'void'
else:
at = ', '.join(map(str, self.argTypes))
return '%s (*)(%s)'%(rt, at)
def getTypedefDef(self, name, printer):
if self.returnType is None:
rt = 'void'
else:
rt = str(self.returnType)
if not self.argTypes:
at = 'void'
else:
at = ', '.join(map(str, self.argTypes))
return 'typedef %s (*%s)(%s);'%(rt, name, at)
###
# Type enumerators
class TypeGenerator(object):
def __init__(self):
self.cache = {}
def setCardinality(self):
abstract
def get(self, N):
T = self.cache.get(N)
if T is None:
assert 0 <= N < self.cardinality
T = self.cache[N] = self.generateType(N)
return T
def generateType(self, N):
abstract
class FixedTypeGenerator(TypeGenerator):
def __init__(self, types):
TypeGenerator.__init__(self)
self.types = types
self.setCardinality()
def setCardinality(self):
self.cardinality = len(self.types)
def generateType(self, N):
return self.types[N]
# Factorial
def fact(n):
result = 1
while n > 0:
result = result * n
n = n - 1
return result
# Compute the number of combinations (n choose k)
def num_combinations(n, k):
return fact(n) / (fact(k) * fact(n - k))
# Enumerate the combinations choosing k elements from the list of values
def combinations(values, k):
# From ActiveState Recipe 190465: Generator for permutations,
# combinations, selections of a sequence
if k==0: yield []
else:
for i in xrange(len(values)-k+1):
for cc in combinations(values[i+1:],k-1):
yield [values[i]]+cc
class EnumTypeGenerator(TypeGenerator):
def __init__(self, values, minEnumerators, maxEnumerators):
TypeGenerator.__init__(self)
self.values = values
self.minEnumerators = minEnumerators
self.maxEnumerators = maxEnumerators
self.setCardinality()
def setCardinality(self):
self.cardinality = 0
for num in range(self.minEnumerators, self.maxEnumerators + 1):
self.cardinality += num_combinations(len(self.values), num)
def generateType(self, n):
# Figure out the number of enumerators in this type
numEnumerators = self.minEnumerators
valuesCovered = 0
while numEnumerators < self.maxEnumerators:
comb = num_combinations(len(self.values), numEnumerators)
if valuesCovered + comb > n:
break
numEnumerators = numEnumerators + 1
valuesCovered += comb
# Find the requested combination of enumerators and build a
# type from it.
i = 0
for enumerators in combinations(self.values, numEnumerators):
if i == n - valuesCovered:
return EnumType(n, enumerators)
i = i + 1
assert False
class ComplexTypeGenerator(TypeGenerator):
def __init__(self, typeGen):
TypeGenerator.__init__(self)
self.typeGen = typeGen
self.setCardinality()
def setCardinality(self):
self.cardinality = self.typeGen.cardinality
def generateType(self, N):
return ComplexType(N, self.typeGen.get(N))
class VectorTypeGenerator(TypeGenerator):
def __init__(self, typeGen, sizes):
TypeGenerator.__init__(self)
self.typeGen = typeGen
self.sizes = tuple(map(int,sizes))
self.setCardinality()
def setCardinality(self):
self.cardinality = len(self.sizes)*self.typeGen.cardinality
def generateType(self, N):
S,T = getNthPairBounded(N, len(self.sizes), self.typeGen.cardinality)
return ArrayType(N, True, self.typeGen.get(T), self.sizes[S])
class FixedArrayTypeGenerator(TypeGenerator):
def __init__(self, typeGen, sizes):
TypeGenerator.__init__(self)
self.typeGen = typeGen
self.sizes = tuple(size)
self.setCardinality()
def setCardinality(self):
self.cardinality = len(self.sizes)*self.typeGen.cardinality
def generateType(self, N):
S,T = getNthPairBounded(N, len(self.sizes), self.typeGen.cardinality)
return ArrayType(N, false, self.typeGen.get(T), self.sizes[S])
class ArrayTypeGenerator(TypeGenerator):
def __init__(self, typeGen, maxSize, useIncomplete=False, useZero=False):
TypeGenerator.__init__(self)
self.typeGen = typeGen
self.useIncomplete = useIncomplete
self.useZero = useZero
self.maxSize = int(maxSize)
self.W = useIncomplete + useZero + self.maxSize
self.setCardinality()
def setCardinality(self):
self.cardinality = self.W * self.typeGen.cardinality
def generateType(self, N):
S,T = getNthPairBounded(N, self.W, self.typeGen.cardinality)
if self.useIncomplete:
if S==0:
size = None
S = None
else:
S = S - 1
if S is not None:
if self.useZero:
size = S
else:
size = S + 1
return ArrayType(N, False, self.typeGen.get(T), size)
class RecordTypeGenerator(TypeGenerator):
def __init__(self, typeGen, useUnion, maxSize):
TypeGenerator.__init__(self)
self.typeGen = typeGen
self.useUnion = bool(useUnion)
self.maxSize = int(maxSize)
self.setCardinality()
def setCardinality(self):
M = 1 + self.useUnion
if self.maxSize is aleph0:
S = aleph0 * self.typeGen.cardinality
else:
S = 0
for i in range(self.maxSize+1):
S += M * (self.typeGen.cardinality ** i)
self.cardinality = S
def generateType(self, N):
isUnion,I = False,N
if self.useUnion:
isUnion,I = (I&1),I>>1
fields = map(self.typeGen.get,getNthTuple(I,self.maxSize,self.typeGen.cardinality))
return RecordType(N, isUnion, fields)
class FunctionTypeGenerator(TypeGenerator):
def __init__(self, typeGen, useReturn, maxSize):
TypeGenerator.__init__(self)
self.typeGen = typeGen
self.useReturn = useReturn
self.maxSize = maxSize
self.setCardinality()
def setCardinality(self):
if self.maxSize is aleph0:
S = aleph0 * self.typeGen.cardinality()
elif self.useReturn:
S = 0
for i in range(1,self.maxSize+1+1):
S += self.typeGen.cardinality ** i
else:
S = 0
for i in range(self.maxSize+1):
S += self.typeGen.cardinality ** i
self.cardinality = S
def generateType(self, N):
if self.useReturn:
# Skip the empty tuple
argIndices = getNthTuple(N+1, self.maxSize+1, self.typeGen.cardinality)
retIndex,argIndices = argIndices[0],argIndices[1:]
retTy = self.typeGen.get(retIndex)
else:
retTy = None
argIndices = getNthTuple(N, self.maxSize, self.typeGen.cardinality)
args = map(self.typeGen.get, argIndices)
return FunctionType(N, retTy, args)
class AnyTypeGenerator(TypeGenerator):
def __init__(self):
TypeGenerator.__init__(self)
self.generators = []
self.bounds = []
self.setCardinality()
self._cardinality = None
def getCardinality(self):
if self._cardinality is None:
return aleph0
else:
return self._cardinality
def setCardinality(self):
self.bounds = [g.cardinality for g in self.generators]
self._cardinality = sum(self.bounds)
cardinality = property(getCardinality, None)
def addGenerator(self, g):
self.generators.append(g)
for i in range(100):
prev = self._cardinality
self._cardinality = None
for g in self.generators:
g.setCardinality()
self.setCardinality()
if (self._cardinality is aleph0) or prev==self._cardinality:
break
else:
raise RuntimeError,"Infinite loop in setting cardinality"
def generateType(self, N):
index,M = getNthPairVariableBounds(N, self.bounds)
return self.generators[index].get(M)
def test():
fbtg = FixedTypeGenerator([BuiltinType('char', 4),
BuiltinType('char', 4, 0),
BuiltinType('int', 4, 5)])
fields1 = AnyTypeGenerator()
fields1.addGenerator( fbtg )
fields0 = AnyTypeGenerator()
fields0.addGenerator( fbtg )
# fields0.addGenerator( RecordTypeGenerator(fields1, False, 4) )
btg = FixedTypeGenerator([BuiltinType('char', 4),
BuiltinType('int', 4)])
etg = EnumTypeGenerator([None, '-1', '1', '1u'], 0, 3)
atg = AnyTypeGenerator()
atg.addGenerator( btg )
atg.addGenerator( RecordTypeGenerator(fields0, False, 4) )
atg.addGenerator( etg )
print 'Cardinality:',atg.cardinality
for i in range(100):
if i == atg.cardinality:
try:
atg.get(i)
raise RuntimeError,"Cardinality was wrong"
except AssertionError:
break
print '%4d: %s'%(i, atg.get(i))
if __name__ == '__main__':
test()

View File

@@ -0,0 +1,15 @@
#!/bin/sh
set -eu
if [ $# != 1 ]; then
echo "usage: $0 <num-tests>"
exit 1
fi
for bits in 32 64; do
for kind in return-types single-args; do
echo "-- $kind-$bits --"
(cd $kind-$bits && ../build-and-summarize.sh $1)
done
done

View File

@@ -0,0 +1,14 @@
#!/bin/sh
set -eu
if [ $# != 1 ]; then
echo "usage: $0 <num-tests>"
exit 1
fi
dir=$(dirname $0)
$dir/build.sh $1 &> /dev/null || true
../summarize.sh $1 &> fails-x.txt
cat fails-x.txt
wc -l fails-x.txt

View File

@@ -0,0 +1,12 @@
#!/bin/sh
set -eu
if [ $# != 1 ]; then
echo "usage: $0 <num-tests>"
exit 1
fi
CPUS=2
make -j $CPUS \
$(for i in $(seq 0 $1); do echo test.$i.report; done) -k

View File

@@ -0,0 +1,68 @@
# Usage: make test.N.report
#
# COUNT can be over-ridden to change the number of tests generated per
# file, and TESTARGS is used to change the type generation. Make sure
# to 'make clean' after changing either of these parameters.
ABITESTGEN := ../ABITestGen.py
TESTARGS := --max-args 0 --test-layout
COUNT := 1000
TIMEOUT := 5
CFLAGS := -std=gnu99
X_COMPILER := llvm-gcc
Y_COMPILER := clang
CC := gcc
ifeq (0, 0)
X_CFLAGS := -m32
Y_CFLAGS := -m32
CC_CFLAGS := -m32
else
X_CFLAGS := -m64
Y_CFLAGS := -m64
CC_CFLAGS := -m64
endif
.PHONY: test.%.report
test.%.report: test.%.x.diff test.%.y.diff
@for t in $^; do \
if [ -s $$t ]; then \
echo "TEST $*: $$t failed"; \
fi; \
done
.PHONY: test.%.build
test.%.build: test.%.ref test.%.x test.%.y
@true
###
.PRECIOUS: test.%.x.diff
test.%.x.diff: test.%.ref.out test.%.x.out
-diff $^ > $@
.PRECIOUS: test.%.y.diff
test.%.y.diff: test.%.ref.out test.%.y.out
-diff $^ > $@
.PRECIOUS: test.%.out
test.%.out: test.%
-./$< > $@
.PRECIOUS: test.%.ref
test.%.ref: test.%.c
$(CC) $(CFLAGS) $(CC_CFLAGS) -o $@ $^
.PRECIOUS: test.%.x
test.%.x: test.%.c
$(X_COMPILER) $(CFLAGS) $(X_CFLAGS) -o $@ $^
.PRECIOUS: test.%.y
test.%.y: test.%.c
$(Y_COMPILER) $(CFLAGS) $(Y_CFLAGS) -o $@ $^
.PRECIOUS: test.%.c
test.%.c: $(ABITESTGEN)
$(ABITESTGEN) $(TESTARGS) -o $@ --min=$(shell expr $* '*' $(COUNT)) --count=$(COUNT)
clean:
rm -f test.* *~

View File

@@ -0,0 +1,7 @@
X_CFLAGS := -m32
Y_CFLAGS := -m32
CC_CFLAGS := -m32
include ../Makefile.test.common
TESTARGS += --max-args 0

View File

@@ -0,0 +1,7 @@
X_CFLAGS := -m64
Y_CFLAGS := -m64
CC_CFLAGS := -m64
include ../Makefile.test.common
TESTARGS += --max-args 0

View File

@@ -0,0 +1,7 @@
X_CFLAGS := -m32
Y_CFLAGS := -m32
CC_CFLAGS := -m32
include ../Makefile.test.common
TESTARGS += --no-function-return --max-args 1

View File

@@ -0,0 +1,13 @@
# Usage: make test.N.report
#
# COUNT can be over-ridden to change the number of tests generated per
# file, and TESTARGS is used to change the type generation. Make sure
# to 'make clean' after changing either of these parameters.
X_CFLAGS := -m64
Y_CFLAGS := -m64
CC_CFLAGS := -m64
include ../Makefile.test.common
TESTARGS += --no-function-return --max-args 1

View File

@@ -0,0 +1,15 @@
#!/bin/sh
set -eu
if [ $# != 1 ]; then
echo "usage: $0 <num-tests>"
exit 1
fi
for i in $(seq 0 $1); do
if (! make test.$i.report &> /dev/null); then
echo "FAIL: $i";
fi;
done

View File

@@ -0,0 +1,44 @@
#!/usr/bin/env python
import sys
from socket import *
from time import strftime
import datetime
def main():
if len(sys.argv) < 4:
print "completion_logger_server.py <listen address> <listen port> <log file>"
exit(1)
host = sys.argv[1]
port = int(sys.argv[2])
buf = 1024 * 8
addr = (host,port)
# Create socket and bind to address
UDPSock = socket(AF_INET,SOCK_DGRAM)
UDPSock.bind(addr)
print "Listing on {0}:{1} and logging to '{2}'".format(host, port, sys.argv[3])
# Open the logging file.
f = open(sys.argv[3], "a")
# Receive messages
while 1:
data,addr = UDPSock.recvfrom(buf)
if not data:
break
else:
f.write("{ ");
f.write("\"time\": \"{0}\"".format(datetime.datetime.utcnow().strftime('%Y-%m-%d %H:%M:%S')))
f.write(", \"sender\": \"{0}\" ".format(addr[0]))
f.write(", \"data\": ")
f.write(data)
f.write(" }\n")
f.flush()
# Close socket
UDPSock.close()
if __name__ == '__main__':
main()

73
external/llvm-project/clang/utils/CaptureCmd vendored Executable file
View File

@@ -0,0 +1,73 @@
#!/usr/bin/env python
"""CaptureCmd - A generic tool for capturing information about the
invocations of another program.
Usage
--
1. Move the original tool to a safe known location.
2. Link CaptureCmd to the original tool's location.
3. Define CAPTURE_CMD_PROGRAM to the known location of the original
tool; this must be an absolute path.
4. Define CAPTURE_CMD_DIR to a directory to write invocation
information to.
"""
import hashlib
import os
import sys
import time
def saveCaptureData(prefix, dir, object):
string = repr(object) + '\n'
key = hashlib.sha1(string).hexdigest()
path = os.path.join(dir,
prefix + key)
if not os.path.exists(path):
f = open(path, 'wb')
f.write(string)
f.close()
return prefix + key
def main():
program = os.getenv('CAPTURE_CMD_PROGRAM')
dir = os.getenv('CAPTURE_CMD_DIR')
fallback = os.getenv('CAPTURE_CMD_FALLBACK')
if not program:
raise ValueError('CAPTURE_CMD_PROGRAM is not defined!')
if not dir:
raise ValueError('CAPTURE_CMD_DIR is not defined!')
# Make the output directory if it doesn't already exist.
if not os.path.exists(dir):
os.mkdir(dir, 0700)
# Get keys for various data.
env = os.environ.items()
env.sort()
envKey = saveCaptureData('env-', dir, env)
cwdKey = saveCaptureData('cwd-', dir, os.getcwd())
argvKey = saveCaptureData('argv-', dir, sys.argv)
entry = (time.time(), envKey, cwdKey, argvKey)
saveCaptureData('cmd-', dir, entry)
if fallback:
pid = os.fork()
if not pid:
os.execv(program, sys.argv)
os._exit(1)
else:
res = os.waitpid(pid, 0)
if not res:
os.execv(fallback, sys.argv)
os._exit(1)
os._exit(res)
else:
os.execv(program, sys.argv)
os._exit(1)
if __name__ == '__main__':
main()

View File

@@ -0,0 +1,161 @@
"""lldb data formatters for clang classes.
Usage
--
import this file in your ~/.lldbinit by adding this line:
command script import /path/to/ClangDataFormat.py
After that, instead of getting this:
(lldb) p Tok.Loc
(clang::SourceLocation) $0 = {
(unsigned int) ID = 123582
}
you'll get:
(lldb) p Tok.Loc
(clang::SourceLocation) $4 = "/usr/include/i386/_types.h:37:1" (offset: 123582, file, local)
"""
import lldb
def __lldb_init_module(debugger, internal_dict):
debugger.HandleCommand("type summary add -F ClangDataFormat.SourceLocation_summary clang::SourceLocation")
debugger.HandleCommand("type summary add -F ClangDataFormat.QualType_summary clang::QualType")
debugger.HandleCommand("type summary add -F ClangDataFormat.StringRef_summary llvm::StringRef")
def SourceLocation_summary(srcloc, internal_dict):
return SourceLocation(srcloc).summary()
def QualType_summary(qualty, internal_dict):
return QualType(qualty).summary()
def StringRef_summary(strref, internal_dict):
return StringRef(strref).summary()
class SourceLocation(object):
def __init__(self, srcloc):
self.srcloc = srcloc
self.ID = srcloc.GetChildAtIndex(0).GetValueAsUnsigned()
self.frame = srcloc.GetFrame()
def offset(self):
return getValueFromExpression(self.srcloc, ".getOffset()").GetValueAsUnsigned()
def isInvalid(self):
return self.ID == 0
def isMacro(self):
return getValueFromExpression(self.srcloc, ".isMacroID()").GetValueAsUnsigned()
def isLocal(self, srcmgr_path):
return self.frame.EvaluateExpression("(%s).isLocalSourceLocation(%s)" % (srcmgr_path, getExpressionPath(self.srcloc))).GetValueAsUnsigned()
def getPrint(self, srcmgr_path):
print_str = getValueFromExpression(self.srcloc, ".printToString(%s)" % srcmgr_path)
return print_str.GetSummary()
def summary(self):
if self.isInvalid():
return "<invalid loc>"
srcmgr_path = findObjectExpressionPath("clang::SourceManager", self.frame)
if srcmgr_path:
return "%s (offset: %d, %s, %s)" % (self.getPrint(srcmgr_path), self.offset(), "macro" if self.isMacro() else "file", "local" if self.isLocal(srcmgr_path) else "loaded")
return "(offset: %d, %s)" % (self.offset(), "macro" if self.isMacro() else "file")
class QualType(object):
def __init__(self, qualty):
self.qualty = qualty
def getAsString(self):
std_str = getValueFromExpression(self.qualty, ".getAsString()")
return std_str.GetSummary()
def summary(self):
desc = self.getAsString()
if desc == '"NULL TYPE"':
return "<NULL TYPE>"
return desc
class StringRef(object):
def __init__(self, strref):
self.strref = strref
self.Data_value = strref.GetChildAtIndex(0)
self.Length = strref.GetChildAtIndex(1).GetValueAsUnsigned()
def summary(self):
if self.Length == 0:
return '""'
data = self.Data_value.GetPointeeData(0, self.Length)
error = lldb.SBError()
string = data.ReadRawData(error, 0, data.GetByteSize())
if error.Fail():
return None
return '"%s"' % string
# Key is a (function address, type name) tuple, value is the expression path for
# an object with such a type name from inside that function.
FramePathMapCache = {}
def findObjectExpressionPath(typename, frame):
func_addr = frame.GetFunction().GetStartAddress().GetFileAddress()
key = (func_addr, typename)
try:
return FramePathMapCache[key]
except KeyError:
#print "CACHE MISS"
path = None
obj = findObject(typename, frame)
if obj:
path = getExpressionPath(obj)
FramePathMapCache[key] = path
return path
def findObject(typename, frame):
def getTypename(value):
# FIXME: lldb should provide something like getBaseType
ty = value.GetType()
if ty.IsPointerType() or ty.IsReferenceType():
return ty.GetPointeeType().GetName()
return ty.GetName()
def searchForType(value, searched):
tyname = getTypename(value)
#print "SEARCH:", getExpressionPath(value), value.GetType().GetName()
if tyname == typename:
return value
ty = value.GetType()
if not (ty.IsPointerType() or
ty.IsReferenceType() or
# FIXME: lldb should provide something like getCanonicalType
tyname.startswith("llvm::IntrusiveRefCntPtr<") or
tyname.startswith("llvm::OwningPtr<")):
return None
# FIXME: Hashing for SBTypes does not seem to work correctly, uses the typename instead,
# and not the canonical one unfortunately.
if tyname in searched:
return None
searched.add(tyname)
for i in range(value.GetNumChildren()):
child = value.GetChildAtIndex(i, 0, False)
found = searchForType(child, searched)
if found:
return found
searched = set()
value_list = frame.GetVariables(True, True, True, True)
for val in value_list:
found = searchForType(val, searched)
if found:
return found if not found.TypeIsPointerType() else found.Dereference()
def getValueFromExpression(val, expr):
return val.GetFrame().EvaluateExpression(getExpressionPath(val) + expr)
def getExpressionPath(val):
stream = lldb.SBStream()
val.GetExpressionPath(stream)
return stream.GetData()

View File

@@ -0,0 +1,7 @@
# Do this by hand instead of using add_llvm_utilities(), which
# tries to create a corresponding executable, which we don't want.
if (LLVM_ADD_NATIVE_VISUALIZERS_TO_SOLUTION)
set(CLANG_VISUALIZERS clang.natvis)
add_custom_target(ClangVisualizers SOURCES ${CLANG_VISUALIZERS})
set_target_properties(ClangVisualizers PROPERTIES FOLDER "Utils")
endif()

File diff suppressed because it is too large Load Diff

215
external/llvm-project/clang/utils/CmpDriver vendored Executable file
View File

@@ -0,0 +1,215 @@
#!/usr/bin/env python
"""
A simple utility that compares tool invocations and exit codes issued by
compiler drivers that support -### (e.g. gcc and clang).
"""
import subprocess
def splitArgs(s):
it = iter(s)
current = ''
inQuote = False
for c in it:
if c == '"':
if inQuote:
inQuote = False
yield current + '"'
else:
inQuote = True
current = '"'
elif inQuote:
if c == '\\':
current += c
current += it.next()
else:
current += c
elif not c.isspace():
yield c
def insertMinimumPadding(a, b, dist):
"""insertMinimumPadding(a,b) -> (a',b')
Return two lists of equal length, where some number of Nones have
been inserted into the shorter list such that sum(map(dist, a',
b')) is minimized.
Assumes dist(X, Y) -> int and non-negative.
"""
def cost(a, b):
return sum(map(dist, a + [None] * (len(b) - len(a)), b))
# Normalize so a is shortest.
if len(b) < len(a):
b, a = insertMinimumPadding(b, a, dist)
return a,b
# For each None we have to insert...
for i in range(len(b) - len(a)):
# For each position we could insert it...
current = cost(a, b)
best = None
for j in range(len(a) + 1):
a_0 = a[:j] + [None] + a[j:]
candidate = cost(a_0, b)
if best is None or candidate < best[0]:
best = (candidate, a_0, j)
a = best[1]
return a,b
class ZipperDiff(object):
"""ZipperDiff - Simple (slow) diff only accommodating inserts."""
def __init__(self, a, b):
self.a = a
self.b = b
def dist(self, a, b):
return a != b
def getDiffs(self):
a,b = insertMinimumPadding(self.a, self.b, self.dist)
for aElt,bElt in zip(a,b):
if self.dist(aElt, bElt):
yield aElt,bElt
class DriverZipperDiff(ZipperDiff):
def isTempFile(self, filename):
if filename[0] != '"' or filename[-1] != '"':
return False
return (filename.startswith('/tmp/', 1) or
filename.startswith('/var/', 1))
def dist(self, a, b):
if a and b and self.isTempFile(a) and self.isTempFile(b):
return 0
return super(DriverZipperDiff, self).dist(a,b)
class CompileInfo:
def __init__(self, out, err, res):
self.commands = []
# Standard out isn't used for much.
self.stdout = out
self.stderr = ''
# FIXME: Compare error messages as well.
for ln in err.split('\n'):
if (ln == 'Using built-in specs.' or
ln.startswith('Target: ') or
ln.startswith('Configured with: ') or
ln.startswith('Thread model: ') or
ln.startswith('gcc version') or
ln.startswith('clang version')):
pass
elif ln.strip().startswith('"'):
self.commands.append(list(splitArgs(ln)))
else:
self.stderr += ln + '\n'
self.stderr = self.stderr.strip()
self.exitCode = res
def captureDriverInfo(cmd, args):
p = subprocess.Popen([cmd,'-###'] + args,
stdin=None,
stdout=subprocess.PIPE,
stderr=subprocess.PIPE)
out,err = p.communicate()
res = p.wait()
return CompileInfo(out,err,res)
def main():
import os, sys
args = sys.argv[1:]
driverA = os.getenv('DRIVER_A') or 'gcc'
driverB = os.getenv('DRIVER_B') or 'clang'
infoA = captureDriverInfo(driverA, args)
infoB = captureDriverInfo(driverB, args)
differ = False
# Compare stdout.
if infoA.stdout != infoB.stdout:
print '-- STDOUT DIFFERS -'
print 'A OUTPUT: ',infoA.stdout
print 'B OUTPUT: ',infoB.stdout
print
diff = ZipperDiff(infoA.stdout.split('\n'),
infoB.stdout.split('\n'))
for i,(aElt,bElt) in enumerate(diff.getDiffs()):
if aElt is None:
print 'A missing: %s' % bElt
elif bElt is None:
print 'B missing: %s' % aElt
else:
print 'mismatch: A: %s' % aElt
print ' B: %s' % bElt
differ = True
# Compare stderr.
if infoA.stderr != infoB.stderr:
print '-- STDERR DIFFERS -'
print 'A STDERR: ',infoA.stderr
print 'B STDERR: ',infoB.stderr
print
diff = ZipperDiff(infoA.stderr.split('\n'),
infoB.stderr.split('\n'))
for i,(aElt,bElt) in enumerate(diff.getDiffs()):
if aElt is None:
print 'A missing: %s' % bElt
elif bElt is None:
print 'B missing: %s' % aElt
else:
print 'mismatch: A: %s' % aElt
print ' B: %s' % bElt
differ = True
# Compare commands.
for i,(a,b) in enumerate(map(None, infoA.commands, infoB.commands)):
if a is None:
print 'A MISSING:',' '.join(b)
differ = True
continue
elif b is None:
print 'B MISSING:',' '.join(a)
differ = True
continue
diff = DriverZipperDiff(a,b)
diffs = list(diff.getDiffs())
if diffs:
print '-- COMMAND %d DIFFERS -' % i
print 'A COMMAND:',' '.join(a)
print 'B COMMAND:',' '.join(b)
print
for i,(aElt,bElt) in enumerate(diffs):
if aElt is None:
print 'A missing: %s' % bElt
elif bElt is None:
print 'B missing: %s' % aElt
else:
print 'mismatch: A: %s' % aElt
print ' B: %s' % bElt
differ = True
# Compare result codes.
if infoA.exitCode != infoB.exitCode:
print '-- EXIT CODES DIFFER -'
print 'A: ',infoA.exitCode
print 'B: ',infoB.exitCode
differ = True
if differ:
sys.exit(1)
if __name__ == '__main__':
main()

910
external/llvm-project/clang/utils/FindSpecRefs vendored Executable file

File diff suppressed because it is too large Load Diff

Some files were not shown because too many files have changed in this diff Show More