TypeGen.py revision 98cca78ecd75704998eea81031bb82f06a9ed5de
1a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar"""Flexible enumeration of C types.""" 2a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar 3a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbarfrom Enumeration import * 4a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar 5a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar# TODO: 6a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar 798cca78ecd75704998eea81031bb82f06a9ed5deDaniel Dunbar# - struct improvements (flexible arrays, packed & 8a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar# unpacked, alignment) 9880c40345f903b087b52eb559cbd435f2ccac484Daniel Dunbar# - objective-c qualified id 10880c40345f903b087b52eb559cbd435f2ccac484Daniel Dunbar# - anonymous / transparent unions 11880c40345f903b087b52eb559cbd435f2ccac484Daniel Dunbar# - VLAs 12880c40345f903b087b52eb559cbd435f2ccac484Daniel Dunbar# - block types 13dda09c8704f47a17ca34e0aa7f3a0d3f8bc6f399Daniel Dunbar# - K&R functions 14dda09c8704f47a17ca34e0aa7f3a0d3f8bc6f399Daniel Dunbar# - pass arguments of different types (test extension, transparent union) 15dda09c8704f47a17ca34e0aa7f3a0d3f8bc6f399Daniel Dunbar# - varargs 16a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar 17a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar### 18a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar# Actual type types 19a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar 2098cca78ecd75704998eea81031bb82f06a9ed5deDaniel Dunbarclass Type: 2198cca78ecd75704998eea81031bb82f06a9ed5deDaniel Dunbar def isBitField(self): 2298cca78ecd75704998eea81031bb82f06a9ed5deDaniel Dunbar return False 2398cca78ecd75704998eea81031bb82f06a9ed5deDaniel Dunbar 2498cca78ecd75704998eea81031bb82f06a9ed5deDaniel Dunbar def isPaddingBitField(self): 2598cca78ecd75704998eea81031bb82f06a9ed5deDaniel Dunbar return False 2698cca78ecd75704998eea81031bb82f06a9ed5deDaniel Dunbar 2798cca78ecd75704998eea81031bb82f06a9ed5deDaniel Dunbarclass BuiltinType(Type): 2898cca78ecd75704998eea81031bb82f06a9ed5deDaniel Dunbar def __init__(self, name, size, bitFieldSize=None): 29a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar self.name = name 30789e4babc9cf78df9565f215a119acad291aea63Daniel Dunbar self.size = size 3198cca78ecd75704998eea81031bb82f06a9ed5deDaniel Dunbar self.bitFieldSize = bitFieldSize 3298cca78ecd75704998eea81031bb82f06a9ed5deDaniel Dunbar 3398cca78ecd75704998eea81031bb82f06a9ed5deDaniel Dunbar def isBitField(self): 3498cca78ecd75704998eea81031bb82f06a9ed5deDaniel Dunbar return self.bitFieldSize is not None 3598cca78ecd75704998eea81031bb82f06a9ed5deDaniel Dunbar 3698cca78ecd75704998eea81031bb82f06a9ed5deDaniel Dunbar def isPaddingBitField(self): 3798cca78ecd75704998eea81031bb82f06a9ed5deDaniel Dunbar return self.bitFieldSize is 0 3898cca78ecd75704998eea81031bb82f06a9ed5deDaniel Dunbar 3998cca78ecd75704998eea81031bb82f06a9ed5deDaniel Dunbar def getBitFieldSize(self): 4098cca78ecd75704998eea81031bb82f06a9ed5deDaniel Dunbar assert self.isBitField() 4198cca78ecd75704998eea81031bb82f06a9ed5deDaniel Dunbar return self.bitFieldSize 42789e4babc9cf78df9565f215a119acad291aea63Daniel Dunbar 43789e4babc9cf78df9565f215a119acad291aea63Daniel Dunbar def sizeof(self): 44789e4babc9cf78df9565f215a119acad291aea63Daniel Dunbar return self.size 45a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar 46a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar def __str__(self): 47a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar return self.name 48a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar 4998cca78ecd75704998eea81031bb82f06a9ed5deDaniel Dunbarclass RecordType(Type): 50a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar def __init__(self, index, isUnion, fields): 51a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar self.index = index 52a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar self.isUnion = isUnion 53a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar self.fields = fields 54a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar self.name = None 55a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar 5698cca78ecd75704998eea81031bb82f06a9ed5deDaniel Dunbar def __str__(self): 5798cca78ecd75704998eea81031bb82f06a9ed5deDaniel Dunbar def getField(t): 5898cca78ecd75704998eea81031bb82f06a9ed5deDaniel Dunbar if t.isBitField(): 5998cca78ecd75704998eea81031bb82f06a9ed5deDaniel Dunbar return "%s : %d;" % (t, t.getBitFieldSize()) 6098cca78ecd75704998eea81031bb82f06a9ed5deDaniel Dunbar else: 6198cca78ecd75704998eea81031bb82f06a9ed5deDaniel Dunbar return "%s;" % t 6298cca78ecd75704998eea81031bb82f06a9ed5deDaniel Dunbar 63a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar return '%s { %s }'%(('struct','union')[self.isUnion], 6498cca78ecd75704998eea81031bb82f06a9ed5deDaniel Dunbar ' '.join(map(getField, self.fields))) 65a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar 66a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar def getTypedefDef(self, name, printer): 6798cca78ecd75704998eea81031bb82f06a9ed5deDaniel Dunbar def getField((i, t)): 6898cca78ecd75704998eea81031bb82f06a9ed5deDaniel Dunbar if t.isBitField(): 6998cca78ecd75704998eea81031bb82f06a9ed5deDaniel Dunbar if t.isPaddingBitField(): 7098cca78ecd75704998eea81031bb82f06a9ed5deDaniel Dunbar return '%s : 0;'%(printer.getTypeName(t),) 7198cca78ecd75704998eea81031bb82f06a9ed5deDaniel Dunbar else: 7298cca78ecd75704998eea81031bb82f06a9ed5deDaniel Dunbar return '%s field%d : %d;'%(printer.getTypeName(t),i, 7398cca78ecd75704998eea81031bb82f06a9ed5deDaniel Dunbar t.getBitFieldSize()) 7498cca78ecd75704998eea81031bb82f06a9ed5deDaniel Dunbar else: 7598cca78ecd75704998eea81031bb82f06a9ed5deDaniel Dunbar return '%s field%d;'%(printer.getTypeName(t),i) 7698cca78ecd75704998eea81031bb82f06a9ed5deDaniel Dunbar fields = map(getField, enumerate(self.fields)) 77a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar # Name the struct for more readable LLVM IR. 78a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar return 'typedef %s %s { %s } %s;'%(('struct','union')[self.isUnion], 79a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar name, ' '.join(fields), name) 80a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar 8198cca78ecd75704998eea81031bb82f06a9ed5deDaniel Dunbarclass ArrayType(Type): 82a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar def __init__(self, index, isVector, elementType, size): 83a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar if isVector: 84a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar # Note that for vectors, this is the size in bytes. 85a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar assert size > 0 86a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar else: 87a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar assert size is None or size >= 0 88a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar self.index = index 89a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar self.isVector = isVector 90a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar self.elementType = elementType 91a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar self.size = size 92789e4babc9cf78df9565f215a119acad291aea63Daniel Dunbar if isVector: 93789e4babc9cf78df9565f215a119acad291aea63Daniel Dunbar eltSize = self.elementType.sizeof() 94789e4babc9cf78df9565f215a119acad291aea63Daniel Dunbar assert not (self.size % eltSize) 95789e4babc9cf78df9565f215a119acad291aea63Daniel Dunbar self.numElements = self.size // eltSize 96789e4babc9cf78df9565f215a119acad291aea63Daniel Dunbar else: 97789e4babc9cf78df9565f215a119acad291aea63Daniel Dunbar self.numElements = self.size 98a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar 99a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar def __str__(self): 100a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar if self.isVector: 101a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar return 'vector (%s)[%d]'%(self.elementType,self.size) 102a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar elif self.size is not None: 103a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar return '(%s)[%d]'%(self.elementType,self.size) 104a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar else: 105a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar return '(%s)[]'%(self.elementType,) 106a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar 107a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar def getTypedefDef(self, name, printer): 108a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar elementName = printer.getTypeName(self.elementType) 109a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar if self.isVector: 110a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar return 'typedef %s %s __attribute__ ((vector_size (%d)));'%(elementName, 111a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar name, 112a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar self.size) 113a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar else: 114a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar if self.size is None: 115a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar sizeStr = '' 116a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar else: 117a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar sizeStr = str(self.size) 118a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar return 'typedef %s %s[%s];'%(elementName, name, sizeStr) 119a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar 12098cca78ecd75704998eea81031bb82f06a9ed5deDaniel Dunbarclass ComplexType(Type): 121a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar def __init__(self, index, elementType): 122a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar self.index = index 123a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar self.elementType = elementType 124a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar 125a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar def __str__(self): 126a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar return '_Complex (%s)'%(self.elementType) 127a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar 128a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar def getTypedefDef(self, name, printer): 129a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar return 'typedef _Complex %s %s;'%(printer.getTypeName(self.elementType), name) 130a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar 13198cca78ecd75704998eea81031bb82f06a9ed5deDaniel Dunbarclass FunctionType(Type): 132a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar def __init__(self, index, returnType, argTypes): 133a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar self.index = index 134a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar self.returnType = returnType 135a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar self.argTypes = argTypes 136a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar 137a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar def __str__(self): 138a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar if self.returnType is None: 139a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar rt = 'void' 140a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar else: 141a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar rt = str(self.returnType) 142a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar if not self.argTypes: 143a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar at = 'void' 144a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar else: 145a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar at = ', '.join(map(str, self.argTypes)) 146a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar return '%s (*)(%s)'%(rt, at) 147a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar 148a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar def getTypedefDef(self, name, printer): 149a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar if self.returnType is None: 150a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar rt = 'void' 151a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar else: 152a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar rt = str(self.returnType) 153a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar if not self.argTypes: 154a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar at = 'void' 155a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar else: 156a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar at = ', '.join(map(str, self.argTypes)) 157a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar return 'typedef %s (*%s)(%s);'%(rt, name, at) 158a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar 159a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar### 160a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar# Type enumerators 161a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar 162a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbarclass TypeGenerator(object): 163a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar def __init__(self): 164a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar self.cache = {} 165a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar 166a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar def setCardinality(self): 167a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar abstract 168a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar 169a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar def get(self, N): 170a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar T = self.cache.get(N) 171a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar if T is None: 172a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar assert 0 <= N < self.cardinality 173a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar T = self.cache[N] = self.generateType(N) 174a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar return T 175a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar 176a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar def generateType(self, N): 177a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar abstract 178a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar 179a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbarclass FixedTypeGenerator(TypeGenerator): 180a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar def __init__(self, types): 181a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar TypeGenerator.__init__(self) 182a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar self.types = types 183a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar self.setCardinality() 184a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar 185a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar def setCardinality(self): 186a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar self.cardinality = len(self.types) 187a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar 188a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar def generateType(self, N): 189a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar return self.types[N] 190a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar 191a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbarclass ComplexTypeGenerator(TypeGenerator): 192a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar def __init__(self, typeGen): 193a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar TypeGenerator.__init__(self) 194a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar self.typeGen = typeGen 195a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar self.setCardinality() 196a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar 197a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar def setCardinality(self): 198a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar self.cardinality = self.typeGen.cardinality 199a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar 200a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar def generateType(self, N): 201a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar return ComplexType(N, self.typeGen.get(N)) 202a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar 203a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbarclass VectorTypeGenerator(TypeGenerator): 204a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar def __init__(self, typeGen, sizes): 205a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar TypeGenerator.__init__(self) 206a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar self.typeGen = typeGen 207a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar self.sizes = tuple(map(int,sizes)) 208a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar self.setCardinality() 209a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar 210a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar def setCardinality(self): 211a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar self.cardinality = len(self.sizes)*self.typeGen.cardinality 212a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar 213a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar def generateType(self, N): 214a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar S,T = getNthPairBounded(N, len(self.sizes), self.typeGen.cardinality) 215a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar return ArrayType(N, True, self.typeGen.get(T), self.sizes[S]) 216a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar 217a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbarclass FixedArrayTypeGenerator(TypeGenerator): 218a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar def __init__(self, typeGen, sizes): 219a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar TypeGenerator.__init__(self) 220a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar self.typeGen = typeGen 221a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar self.sizes = tuple(size) 222a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar self.setCardinality() 223a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar 224a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar def setCardinality(self): 225a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar self.cardinality = len(self.sizes)*self.typeGen.cardinality 226a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar 227a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar def generateType(self, N): 228a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar S,T = getNthPairBounded(N, len(self.sizes), self.typeGen.cardinality) 229a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar return ArrayType(N, false, self.typeGen.get(T), self.sizes[S]) 230a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar 231a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbarclass ArrayTypeGenerator(TypeGenerator): 232a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar def __init__(self, typeGen, maxSize, useIncomplete=False, useZero=False): 233a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar TypeGenerator.__init__(self) 234a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar self.typeGen = typeGen 235a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar self.useIncomplete = useIncomplete 236a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar self.useZero = useZero 237a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar self.maxSize = int(maxSize) 238a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar self.W = useIncomplete + useZero + self.maxSize 239a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar self.setCardinality() 240a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar 241a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar def setCardinality(self): 242a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar self.cardinality = self.W * self.typeGen.cardinality 243a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar 244a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar def generateType(self, N): 245a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar S,T = getNthPairBounded(N, self.W, self.typeGen.cardinality) 246a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar if self.useIncomplete: 247a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar if S==0: 248a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar size = None 249a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar S = None 250a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar else: 251a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar S = S - 1 252a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar if S is not None: 253a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar if self.useZero: 254a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar size = S 255a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar else: 256a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar size = S + 1 257a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar return ArrayType(N, False, self.typeGen.get(T), size) 258a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar 259a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbarclass RecordTypeGenerator(TypeGenerator): 260a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar def __init__(self, typeGen, useUnion, maxSize): 261a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar TypeGenerator.__init__(self) 262a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar self.typeGen = typeGen 263a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar self.useUnion = bool(useUnion) 264a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar self.maxSize = int(maxSize) 265a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar self.setCardinality() 266a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar 267a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar def setCardinality(self): 268a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar M = 1 + self.useUnion 269a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar if self.maxSize is aleph0: 270a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar S = aleph0 * self.typeGen.cardinality 271a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar else: 272a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar S = 0 273a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar for i in range(self.maxSize+1): 274a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar S += M * (self.typeGen.cardinality ** i) 275a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar self.cardinality = S 276a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar 277a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar def generateType(self, N): 278a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar isUnion,I = False,N 279a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar if self.useUnion: 280a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar isUnion,I = (I&1),I>>1 281a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar fields = map(self.typeGen.get,getNthTuple(I,self.maxSize,self.typeGen.cardinality)) 282a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar return RecordType(N, isUnion, fields) 283a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar 284a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbarclass FunctionTypeGenerator(TypeGenerator): 285a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar def __init__(self, typeGen, useReturn, maxSize): 286a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar TypeGenerator.__init__(self) 287a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar self.typeGen = typeGen 288a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar self.useReturn = useReturn 289a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar self.maxSize = maxSize 290a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar self.setCardinality() 291a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar 292a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar def setCardinality(self): 293a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar if self.maxSize is aleph0: 294a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar S = aleph0 * self.typeGen.cardinality() 295a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar elif self.useReturn: 296a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar S = 0 297a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar for i in range(1,self.maxSize+1+1): 298a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar S += self.typeGen.cardinality ** i 299a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar else: 300a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar S = 0 301a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar for i in range(self.maxSize+1): 302a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar S += self.typeGen.cardinality ** i 303a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar self.cardinality = S 304a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar 305a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar def generateType(self, N): 306a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar if self.useReturn: 307a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar # Skip the empty tuple 308a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar argIndices = getNthTuple(N+1, self.maxSize+1, self.typeGen.cardinality) 309a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar retIndex,argIndices = argIndices[0],argIndices[1:] 310a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar retTy = self.typeGen.get(retIndex) 311a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar else: 312a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar retTy = None 313a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar argIndices = getNthTuple(N, self.maxSize, self.typeGen.cardinality) 314a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar args = map(self.typeGen.get, argIndices) 315a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar return FunctionType(N, retTy, args) 316a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar 317a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbarclass AnyTypeGenerator(TypeGenerator): 318a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar def __init__(self): 319a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar TypeGenerator.__init__(self) 320a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar self.generators = [] 321a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar self.bounds = [] 322a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar self.setCardinality() 323a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar self._cardinality = None 324a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar 325a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar def getCardinality(self): 326a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar if self._cardinality is None: 327a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar return aleph0 328a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar else: 329a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar return self._cardinality 330a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar def setCardinality(self): 331a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar self.bounds = [g.cardinality for g in self.generators] 332a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar self._cardinality = sum(self.bounds) 333a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar cardinality = property(getCardinality, None) 334a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar 335a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar def addGenerator(self, g): 336a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar self.generators.append(g) 337a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar for i in range(100): 338a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar prev = self._cardinality 339a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar self._cardinality = None 340a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar for g in self.generators: 341a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar g.setCardinality() 342a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar self.setCardinality() 343a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar if (self._cardinality is aleph0) or prev==self._cardinality: 344a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar break 345a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar else: 346a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar raise RuntimeError,"Infinite loop in setting cardinality" 347a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar 348a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar def generateType(self, N): 349a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar index,M = getNthPairVariableBounds(N, self.bounds) 350a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar return self.generators[index].get(M) 351a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar 352a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbardef test(): 35398cca78ecd75704998eea81031bb82f06a9ed5deDaniel Dunbar fbtg = FixedTypeGenerator([BuiltinType('char', 4), 35498cca78ecd75704998eea81031bb82f06a9ed5deDaniel Dunbar BuiltinType('char', 4, 0), 35598cca78ecd75704998eea81031bb82f06a9ed5deDaniel Dunbar BuiltinType('int', 4, 5)]) 35698cca78ecd75704998eea81031bb82f06a9ed5deDaniel Dunbar 35798cca78ecd75704998eea81031bb82f06a9ed5deDaniel Dunbar fields1 = AnyTypeGenerator() 35898cca78ecd75704998eea81031bb82f06a9ed5deDaniel Dunbar fields1.addGenerator( fbtg ) 35998cca78ecd75704998eea81031bb82f06a9ed5deDaniel Dunbar 36098cca78ecd75704998eea81031bb82f06a9ed5deDaniel Dunbar fields0 = AnyTypeGenerator() 36198cca78ecd75704998eea81031bb82f06a9ed5deDaniel Dunbar fields0.addGenerator( fbtg ) 36298cca78ecd75704998eea81031bb82f06a9ed5deDaniel Dunbar# fields0.addGenerator( RecordTypeGenerator(fields1, False, 4) ) 36398cca78ecd75704998eea81031bb82f06a9ed5deDaniel Dunbar 36498cca78ecd75704998eea81031bb82f06a9ed5deDaniel Dunbar btg = FixedTypeGenerator([BuiltinType('char', 4), 36598cca78ecd75704998eea81031bb82f06a9ed5deDaniel Dunbar BuiltinType('int', 4)]) 36698cca78ecd75704998eea81031bb82f06a9ed5deDaniel Dunbar 367a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar atg = AnyTypeGenerator() 368a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar atg.addGenerator( btg ) 36998cca78ecd75704998eea81031bb82f06a9ed5deDaniel Dunbar atg.addGenerator( RecordTypeGenerator(fields0, False, 4) ) 370a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar print 'Cardinality:',atg.cardinality 371a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar for i in range(100): 37298cca78ecd75704998eea81031bb82f06a9ed5deDaniel Dunbar if i == atg.cardinality: 37398cca78ecd75704998eea81031bb82f06a9ed5deDaniel Dunbar try: 37498cca78ecd75704998eea81031bb82f06a9ed5deDaniel Dunbar atg.get(i) 37598cca78ecd75704998eea81031bb82f06a9ed5deDaniel Dunbar raise RuntimeError,"Cardinality was wrong" 37698cca78ecd75704998eea81031bb82f06a9ed5deDaniel Dunbar except AssertionError: 37798cca78ecd75704998eea81031bb82f06a9ed5deDaniel Dunbar break 378a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar print '%4d: %s'%(i, atg.get(i)) 379a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar 380a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbarif __name__ == '__main__': 381a1bfe638c03c517b110f55962adb882f47131667Daniel Dunbar test() 382