#include #include #include #include #include using namespace std; static struct{ const string name; bool isFloat; bool hasComparison; } basicTypes[] = { // { "char" , false, true , }, // { "signed char" , false, true , }, // { "unsigned char" , false, true , }, { "signed short" , false, true , }, { "unsigned short" , false, true , }, { "signed int" , false, true , }, { "unsigned int" , false, true , }, { "signed long int" , false, true , }, { "unsigned long int" , false, true , }, { "signed long long int" , false, true , }, { "unsigned long long int", false, true , }, { "float" , true , true , }, { "double" , true , true , }, { "long double" , true , true , }, { "float _Complex" , true , false, }, { "double _Complex" , true , false, }, { "long double _Complex" , true , false, }, #if defined(__SIZEOF_INT128__) { "__int128" , false, true , }, { "unsigned __int128" , false, true , }, #endif #if defined(__i386__) || defined(__ia64__) || defined(__x86_64__) { "__float80" , true , true , }, { "_Float128" , true , true , }, #endif }; struct { const string name; bool assignment = false; bool floatCompat = true; bool isComparison = false; bool isEqual = false; } arithmeticOperators[] = { { "?++" , true , true, false, false }, { "?--" , true , true, false, false }, { "++?" , true , true, false, false }, { "--?" , true , true, false, false }, { "+?" , false, true , false, false }, { "-?" , false, true , false, false }, { "~?" , false, false, false, false }, { "!?" , false, true , false, true }, { "?*?" , false, true , false, false }, { "?/?" , false, true , false, false }, { "?%?" , false, false, false, false }, { "?+?" , false, true , false, false }, { "?-?" , false, true , false, false }, { "?<>?" , false, false, false, false }, { "??" , false, true , true , false }, { "?>=?" , false, true , true , true }, { "?==?" , false, true , false, true }, { "?!=?" , false, true , false, true }, { "?&?" , false, false, false, false }, { "?^?" , false, false, false, false }, { "?|?" , false, false, false, false }, { "?=?" , true , true , false, false }, { "?+=?" , true , true , false, false }, { "?-=?" , true , true , false, false }, { "?*=?" , true , true , false, false }, { "?/=?" , true , true , false, false }, { "?%=?" , true , false, false, false }, { "?<<=?", true , false, false, false }, { "?>>=?", true , false, false, false }, { "?&=?" , true , false, false, false }, { "?|=?" , true , false, false, false }, { "?^=?" , true , false, false, false }, }; enum ArgType { Normal, PtrDiff, CommPtrDiff }; struct { const string name; bool assignment = false; string diffReturn; ArgType diffArg2 = Normal; string sized; } pointerOperators[] = { { "?++", true, "", Normal, " | sized(DT)" }, { "?--", true, "", Normal, " | sized(DT)" }, { "++?", true, "", Normal, " | sized(DT)" }, { "--?", true, "", Normal, " | sized(DT)" }, { "!?" , false, "int", Normal, "" }, { "??", false, "signed int", Normal, "" }, { "?>=?", false, "signed int", Normal, "" }, { "?==?", false, "signed int", Normal, "" }, { "?!=?", false, "signed int", Normal, "" }, { "?=?", true, "", Normal, "" }, // void * LHS, zero_t RHS ??? { "*?", false, "&", Normal, " | sized(DT)" }, // & ??? { "?-?", false, "ptrdiff_t", Normal, " | sized(DT)" }, { "?-?", false, "", PtrDiff, " | sized(DT)" }, { "?-=?", true, "", PtrDiff, " | sized(DT)" }, { "?+?", false, "", CommPtrDiff, " | sized(DT)" }, { "?[?]", false, "&", CommPtrDiff, " | sized(DT)" }, // & ??? { "?+=?" , true, "", PtrDiff, " | sized(DT)" }, }; template string mask2string(unsigned int mask, array names) { string result = ""; int i = 0; for(auto name : names) { if(mask & (1 << i)) { result += name; } else { result.append(name.size(), ' '); } i++; } return result; } template constexpr auto make_array(T&&... values) -> std::array< typename std::decay::type>::type, sizeof...(T)> { return std::array< typename std::decay< typename std::common_type::type>::type, sizeof...(T)>{{std::forward(values)...}}; } int main() { cout << "# 2 \"prelude.cfa\" // needed for error messages from this file" << endl; cout << "trait sized(dtype T) {};" << endl; cout << "//////////////////////////" << endl; cout << "// Arithmetic Operators //" << endl; cout << "//////////////////////////" << endl; cout << endl; cout << "signed int ?==?( zero_t, zero_t ), ?!=?( zero_t, zero_t );" << endl; cout << "signed int ?==?( one_t, one_t ), ?!=?( one_t, one_t );" << endl; cout << "signed int ?==?( _Bool, _Bool ), ?!=?( _Bool, _Bool );" << endl; cout << "signed int !?( _Bool );" << endl; for (auto op : arithmeticOperators) { for (auto type : basicTypes ) { auto operands = count(op.name.begin(), op.name.end(), '?'); if (! op.floatCompat && type.isFloat) continue; if (op.isComparison && ! type.hasComparison) continue; if (op.assignment) { const char * qualifiers[] = { "", "volatile " }; for (auto q : qualifiers){ cout << type.name << " " << op.name << "("; cout << q << type.name << " &"; for (int i = 1; i < operands; ++i) { cout << ", " << type.name; } cout << ");" << endl; } } else { if (op.isComparison || op.isEqual) cout << "signed int"; else cout << type.name; cout << " " << op.name << "("; for (int i = 0; i < operands; ++i) { cout << type.name; if ((i+1) != operands) cout << ", "; } cout << ");" << endl; } } cout << endl; } cout << endl; cout << "/////////////////////////////" << endl; cout << "// Arithmetic Constructors //" << endl; cout << "/////////////////////////////" << endl; auto otype = [](const std::string & type, bool do_volatile = false) { cout << "void \t?{} ( " << type << " & );" << endl; cout << "void \t?{} ( " << type << " &, " << type << " );" << endl; cout << type << " \t?=? ( " << type << " &, " << type << " )"; if( do_volatile ) { cout << ", \t?=?( volatile " << type << " &, " << type << " )"; } cout << ";" << endl; cout << "void \t^?{}( " << type << " & );" << endl; }; otype("zero_t"); otype("one_t"); otype("_Bool", true); otype("char", true); otype("signed char", true); otype("unsigned char", true); for (auto type : basicTypes) { cout << "void ?{}(" << type.name << " &);" << endl; cout << "void ?{}(" << type.name << " &, " << type.name << ");" << endl; cout << "void ^?{}(" << type.name << " &);" << endl; cout << endl; } cout << endl; cout << "//////////////////////////" << endl; cout << "// Pointer Constructors //" << endl; cout << "//////////////////////////" << endl; cout << "forall(ftype FT) void ?{}( FT *&, FT * );" << endl; cout << "forall(ftype FT) void ?{}( FT * volatile &, FT * );" << endl; // generate qualifiers vector qualifiersSingle; vector> qualifiersPair; const unsigned int NQ = 2; for(unsigned int lhs = 0; lhs < (1<