1#!/usr/bin/python 2 3import sys, re; 4from structs import unions, structs, defines; 5 6# command line arguments 7arch = sys.argv[1]; 8outfile = sys.argv[2]; 9infiles = sys.argv[3:]; 10 11 12########################################################################### 13# configuration #2: architecture information 14 15inttypes = {}; 16header = {}; 17footer = {}; 18 19#arm 20inttypes["arm32"] = { 21 "unsigned long" : "__danger_unsigned_long_on_arm32", 22 "long" : "__danger_long_on_arm32", 23 "xen_pfn_t" : "uint64_t", 24 "xen_ulong_t" : "uint64_t", 25 "uint64_t" : "__align8__ uint64_t", 26}; 27header["arm32"] = """ 28#define __arm___ARM32 1 29#if defined(__GNUC__) && !defined(__STRICT_ANSI__) 30# define __DECL_REG(n64, n32) union { uint64_t n64; uint32_t n32; } 31# define __align8__ __attribute__((aligned (8))) 32#else 33# define __DECL_REG(n64, n32) uint64_t n64 34# define __align8__ FIXME 35#endif 36"""; 37footer["arm32"] = """ 38#undef __DECL_REG 39""" 40 41inttypes["arm64"] = { 42 "unsigned long" : "__danger_unsigned_long_on_arm64", 43 "long" : "__danger_long_on_arm64", 44 "xen_pfn_t" : "uint64_t", 45 "xen_ulong_t" : "uint64_t", 46 "uint64_t" : "__align8__ uint64_t", 47}; 48header["arm64"] = """ 49#define __aarch64___ARM64 1 50#if defined(__GNUC__) && !defined(__STRICT_ANSI__) 51# define __DECL_REG(n64, n32) union { uint64_t n64; uint32_t n32; } 52# define __align8__ __attribute__((aligned (8))) 53#else 54# define __DECL_REG(n64, n32) uint64_t n64 55# define __align8__ FIXME 56#endif 57"""; 58footer["arm64"] = """ 59#undef __DECL_REG 60""" 61 62# x86_32 63inttypes["x86_32"] = { 64 "unsigned long" : "uint32_t", 65 "long" : "uint32_t", 66 "xen_pfn_t" : "uint32_t", 67 "xen_ulong_t" : "uint32_t", 68}; 69header["x86_32"] = """ 70#define __DECL_REG_LO8(which) uint32_t e ## which ## x 71#define __DECL_REG_LO16(name) uint32_t e ## name 72#define __i386___X86_32 1 73#pragma pack(4) 74"""; 75footer["x86_32"] = """ 76#undef __DECL_REG_LO8 77#undef __DECL_REG_LO16 78#pragma pack() 79"""; 80 81# x86_64 82inttypes["x86_64"] = { 83 "unsigned long" : "__align8__ uint64_t", 84 "long" : "__align8__ uint64_t", 85 "xen_pfn_t" : "__align8__ uint64_t", 86 "xen_ulong_t" : "__align8__ uint64_t", 87}; 88header["x86_64"] = """ 89#if defined(__GNUC__) && !defined(__STRICT_ANSI__) 90# define __DECL_REG(name) union { uint64_t r ## name, e ## name; } 91# define __align8__ __attribute__((aligned (8))) 92#else 93# define __DECL_REG(name) uint64_t r ## name 94# define __align8__ FIXME 95#endif 96#define __DECL_REG_LOHI(name) __DECL_REG(name ## x) 97#define __DECL_REG_LO8 __DECL_REG 98#define __DECL_REG_LO16 __DECL_REG 99#define __DECL_REG_HI __DECL_REG 100#define __x86_64___X86_64 1 101"""; 102footer["x86_64"] = """ 103#undef __DECL_REG 104#undef __DECL_REG_LOHI 105#undef __DECL_REG_LO8 106#undef __DECL_REG_LO16 107#undef __DECL_REG_HI 108""" 109 110########################################################################### 111# main 112 113input = ""; 114output = ""; 115fileid = re.sub("[-.]", "_", "__FOREIGN_%s__" % outfile.upper()); 116 117# read input header files 118for name in infiles: 119 f = open(name, "r"); 120 input += f.read(); 121 f.close(); 122 123# add header 124output += """ 125/* 126 * public xen defines and struct for %s 127 * generated by %s -- DO NOT EDIT 128 */ 129 130#ifndef %s 131#define %s 1 132 133""" % (arch, sys.argv[0], fileid, fileid) 134 135if arch in header: 136 output += header[arch]; 137 output += "\n"; 138 139defined = {} 140 141# add defines to output 142for line in re.findall("#define[^\n]+", input): 143 for define in defines: 144 regex = "#define\s+%s\\b" % define; 145 match = re.search(regex, line); 146 if None == match: 147 continue; 148 defined[define] = 1 149 if define.upper()[0] == define[0]: 150 replace = define + "_" + arch.upper(); 151 else: 152 replace = define + "_" + arch; 153 regex = "\\b%s\\b" % define; 154 output += re.sub(regex, replace, line) + "\n"; 155output += "\n"; 156 157# delete defines, comments, empty lines 158input = re.sub("#define[^\n]+\n", "", input); 159input = re.compile("/\*(.*?)\*/", re.S).sub("", input) 160input = re.compile("\n\s*\n", re.S).sub("\n", input); 161 162# add unions to output 163for union in unions: 164 regex = "union\s+%s\s*\{(.*?)\n\};" % union; 165 match = re.search(regex, input, re.S) 166 if None == match: 167 output += "#define %s_has_no_%s 1\n" % (arch, union); 168 else: 169 output += "union %s_%s {%s\n};\n" % (union, arch, match.group(1)); 170 output += "\n"; 171 172# add structs to output 173for struct in structs: 174 regex = "(?:#ifdef ([A-Z_]+))?\nstruct\s+%s\s*\{(.*?)\n\};" % struct; 175 match = re.search(regex, input, re.S) 176 if None == match or \ 177 (match.group(1) is not None and match.group(1) not in defined): 178 output += "#define %s_has_no_%s 1\n" % (arch, struct); 179 else: 180 output += "struct %s_%s {%s\n};\n" % (struct, arch, match.group(2)); 181 output += "typedef struct %s_%s %s_%s_t;\n" % (struct, arch, struct, arch); 182 output += "\n"; 183 184# add footer 185if arch in footer: 186 output += footer[arch]; 187 output += "\n"; 188output += "#endif /* %s */\n" % fileid; 189 190# replace: defines 191for define in defines: 192 if define.upper()[0] == define[0]: 193 replace = define + "_" + arch.upper(); 194 else: 195 replace = define + "_" + arch; 196 output = re.sub("\\b%s\\b" % define, replace, output); 197 198# replace: unions 199for union in unions: 200 output = re.sub("\\b(union\s+%s)\\b" % union, "\\1_%s" % arch, output); 201 202# replace: structs + struct typedefs 203for struct in structs: 204 output = re.sub("\\b(struct\s+%s)\\b" % struct, "\\1_%s" % arch, output); 205 output = re.sub("\\b(%s)_t\\b" % struct, "\\1_%s_t" % arch, output); 206 207# replace: integer types 208integers = inttypes[arch].keys(); 209integers.sort(lambda a, b: cmp(len(b),len(a))); 210for type in integers: 211 output = re.sub("\\b%s\\b" % type, inttypes[arch][type], output); 212 213# print results 214f = open(outfile, "w"); 215f.write(output); 216f.close; 217 218