aboutsummaryrefslogtreecommitdiff
path: root/lib
diff options
context:
space:
mode:
authorAlisdair Meredith <public@alisdairm.net>2009-07-14 06:30:34 +0000
committerAlisdair Meredith <public@alisdairm.net>2009-07-14 06:30:34 +0000
commitf5c209d23b20ada4a9b6235db50317239cbf6ae1 (patch)
tree86513b9161dcbc74e0684bd1e0c6b26b47afe712 /lib
parent127bf318068659471bce3b08c462d2eab6a5e6a5 (diff)
Basic support for C++0x unicode types. Support for literals will follow in an incremental patch
git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@75622 91177308-0d34-0410-b5e6-96231b3b80d8
Diffstat (limited to 'lib')
-rw-r--r--lib/AST/ASTContext.cpp24
-rw-r--r--lib/AST/Type.cpp2
-rw-r--r--lib/Basic/TargetInfo.cpp4
-rw-r--r--lib/CodeGen/CodeGenTypes.cpp2
-rw-r--r--lib/CodeGen/Mangle.cpp6
-rw-r--r--lib/Frontend/PCHReader.cpp2
-rw-r--r--lib/Frontend/PCHWriter.cpp2
-rw-r--r--lib/Lex/PPExpressions.cpp4
-rw-r--r--lib/Parse/DeclSpec.cpp2
-rw-r--r--lib/Parse/ParseDecl.cpp19
-rw-r--r--lib/Parse/ParseExpr.cpp2
-rw-r--r--lib/Parse/ParseExprCXX.cpp6
-rw-r--r--lib/Parse/ParseTentative.cpp2
-rw-r--r--lib/Sema/SemaOverload.cpp3
-rw-r--r--lib/Sema/SemaType.cpp10
15 files changed, 86 insertions, 4 deletions
diff --git a/lib/AST/ASTContext.cpp b/lib/AST/ASTContext.cpp
index 5de66596e1..9d1e1267e4 100644
--- a/lib/AST/ASTContext.cpp
+++ b/lib/AST/ASTContext.cpp
@@ -170,6 +170,16 @@ void ASTContext::InitBuiltinTypes() {
else // C99
WCharTy = getFromTargetType(Target.getWCharType());
+ if (LangOpts.CPlusPlus) // C++0x 3.9.1p5, extension for C++
+ InitBuiltinType(Char16Ty, BuiltinType::Char16);
+ else // C99
+ Char16Ty = getFromTargetType(Target.getChar16Type());
+
+ if (LangOpts.CPlusPlus) // C++0x 3.9.1p5, extension for C++
+ InitBuiltinType(Char32Ty, BuiltinType::Char32);
+ else // C99
+ Char32Ty = getFromTargetType(Target.getChar32Type());
+
// Placeholder type for functions.
InitBuiltinType(OverloadTy, BuiltinType::Overload);
@@ -522,6 +532,14 @@ ASTContext::getTypeInfo(const Type *T) {
Width = Target.getWCharWidth();
Align = Target.getWCharAlign();
break;
+ case BuiltinType::Char16:
+ Width = Target.getChar16Width();
+ Align = Target.getChar16Align();
+ break;
+ case BuiltinType::Char32:
+ Width = Target.getChar32Width();
+ Align = Target.getChar32Align();
+ break;
case BuiltinType::UShort:
case BuiltinType::Short:
Width = Target.getShortWidth();
@@ -2326,6 +2344,12 @@ unsigned ASTContext::getIntegerRank(Type *T) {
if (T->isSpecificBuiltinType(BuiltinType::WChar))
T = getFromTargetType(Target.getWCharType()).getTypePtr();
+ if (T->isSpecificBuiltinType(BuiltinType::Char16))
+ T = getFromTargetType(Target.getChar16Type()).getTypePtr();
+
+ if (T->isSpecificBuiltinType(BuiltinType::Char32))
+ T = getFromTargetType(Target.getChar32Type()).getTypePtr();
+
// There are two things which impact the integer rank: the width, and
// the ordering of builtins. The builtin ordering is encoded in the
// bottom three bits; the width is encoded in the bits above that.
diff --git a/lib/AST/Type.cpp b/lib/AST/Type.cpp
index 7a9faac60f..9edb9c046d 100644
--- a/lib/AST/Type.cpp
+++ b/lib/AST/Type.cpp
@@ -1003,6 +1003,8 @@ const char *BuiltinType::getName(const LangOptions &LO) const {
case Double: return "double";
case LongDouble: return "long double";
case WChar: return "wchar_t";
+ case Char16: return "char16_t";
+ case Char32: return "char32_t";
case NullPtr: return "nullptr_t";
case Overload: return "<overloaded function type>";
case Dependent: return "<dependent type>";
diff --git a/lib/Basic/TargetInfo.cpp b/lib/Basic/TargetInfo.cpp
index ba7f190408..5b2ffb7d16 100644
--- a/lib/Basic/TargetInfo.cpp
+++ b/lib/Basic/TargetInfo.cpp
@@ -25,6 +25,8 @@ TargetInfo::TargetInfo(const std::string &T) : Triple(T) {
TLSSupported = true;
PointerWidth = PointerAlign = 32;
WCharWidth = WCharAlign = 32;
+ Char16Width = Char16Align = 16;
+ Char32Width = Char32Align = 32;
IntWidth = IntAlign = 32;
LongWidth = LongAlign = 32;
LongLongWidth = LongLongAlign = 64;
@@ -41,6 +43,8 @@ TargetInfo::TargetInfo(const std::string &T) : Triple(T) {
UIntMaxType = UnsignedLongLong;
IntPtrType = SignedLong;
WCharType = SignedInt;
+ Char16Type = UnsignedShort;
+ Char32Type = UnsignedInt;
Int64Type = SignedLongLong;
FloatFormat = &llvm::APFloat::IEEEsingle;
DoubleFormat = &llvm::APFloat::IEEEdouble;
diff --git a/lib/CodeGen/CodeGenTypes.cpp b/lib/CodeGen/CodeGenTypes.cpp
index 6add2c25c7..5ed2b7c2a0 100644
--- a/lib/CodeGen/CodeGenTypes.cpp
+++ b/lib/CodeGen/CodeGenTypes.cpp
@@ -249,6 +249,8 @@ const llvm::Type *CodeGenTypes::ConvertNewType(QualType T) {
case BuiltinType::LongLong:
case BuiltinType::ULongLong:
case BuiltinType::WChar:
+ case BuiltinType::Char16:
+ case BuiltinType::Char32:
return llvm::IntegerType::get(
static_cast<unsigned>(Context.getTypeSize(T)));
diff --git a/lib/CodeGen/Mangle.cpp b/lib/CodeGen/Mangle.cpp
index 97c26f87b1..cd0e2eae7d 100644
--- a/lib/CodeGen/Mangle.cpp
+++ b/lib/CodeGen/Mangle.cpp
@@ -540,8 +540,8 @@ void CXXNameMangler::mangleType(const BuiltinType *T) {
// UNSUPPORTED: ::= De # IEEE 754r decimal floating point (128 bits)
// UNSUPPORTED: ::= Df # IEEE 754r decimal floating point (32 bits)
// UNSUPPORTED: ::= Dh # IEEE 754r half-precision floating point (16 bits)
- // UNSUPPORTED: ::= Di # char32_t
- // UNSUPPORTED: ::= Ds # char16_t
+ // ::= Di # char32_t
+ // ::= Ds # char16_t
// ::= u <source-name> # vendor extended type
// From our point of view, std::nullptr_t is a builtin, but as far as mangling
// is concerned, it's a type called std::nullptr_t.
@@ -557,6 +557,8 @@ void CXXNameMangler::mangleType(const BuiltinType *T) {
case BuiltinType::UInt128: Out << 'o'; break;
case BuiltinType::SChar: Out << 'a'; break;
case BuiltinType::WChar: Out << 'w'; break;
+ case BuiltinType::Char16: Out << "Ds"; break;
+ case BuiltinType::Char32: Out << "Di"; break;
case BuiltinType::Short: Out << 's'; break;
case BuiltinType::Int: Out << 'i'; break;
case BuiltinType::Long: Out << 'l'; break;
diff --git a/lib/Frontend/PCHReader.cpp b/lib/Frontend/PCHReader.cpp
index c922b0d6db..012c6fecfe 100644
--- a/lib/Frontend/PCHReader.cpp
+++ b/lib/Frontend/PCHReader.cpp
@@ -1984,6 +1984,8 @@ QualType PCHReader::GetType(pch::TypeID ID) {
case pch::PREDEF_TYPE_OVERLOAD_ID: T = Context->OverloadTy; break;
case pch::PREDEF_TYPE_DEPENDENT_ID: T = Context->DependentTy; break;
case pch::PREDEF_TYPE_NULLPTR_ID: T = Context->NullPtrTy; break;
+ case pch::PREDEF_TYPE_CHAR16_ID: T = Context->Char16Ty; break;
+ case pch::PREDEF_TYPE_CHAR32_ID: T = Context->Char32Ty; break;
}
assert(!T.isNull() && "Unknown predefined type");
diff --git a/lib/Frontend/PCHWriter.cpp b/lib/Frontend/PCHWriter.cpp
index 57577b7dfa..333bcc9893 100644
--- a/lib/Frontend/PCHWriter.cpp
+++ b/lib/Frontend/PCHWriter.cpp
@@ -2005,6 +2005,8 @@ void PCHWriter::AddTypeRef(QualType T, RecordData &Record) {
case BuiltinType::Double: ID = pch::PREDEF_TYPE_DOUBLE_ID; break;
case BuiltinType::LongDouble: ID = pch::PREDEF_TYPE_LONGDOUBLE_ID; break;
case BuiltinType::NullPtr: ID = pch::PREDEF_TYPE_NULLPTR_ID; break;
+ case BuiltinType::Char16: ID = pch::PREDEF_TYPE_CHAR16_ID; break;
+ case BuiltinType::Char32: ID = pch::PREDEF_TYPE_CHAR32_ID; break;
case BuiltinType::Overload: ID = pch::PREDEF_TYPE_OVERLOAD_ID; break;
case BuiltinType::Dependent: ID = pch::PREDEF_TYPE_DEPENDENT_ID; break;
case BuiltinType::UndeducedAuto:
diff --git a/lib/Lex/PPExpressions.cpp b/lib/Lex/PPExpressions.cpp
index c98acc4deb..a7307c6b56 100644
--- a/lib/Lex/PPExpressions.cpp
+++ b/lib/Lex/PPExpressions.cpp
@@ -224,8 +224,10 @@ static bool EvaluateValue(PPValue &Result, Token &PeekTok, DefinedTracker &DT,
unsigned NumBits;
if (Literal.isMultiChar())
NumBits = TI.getIntWidth();
+ else if (Literal.isWide())
+ NumBits = TI.getWCharWidth();
else
- NumBits = TI.getCharWidth(Literal.isWide());
+ NumBits = TI.getCharWidth();
// Set the width.
llvm::APSInt Val(NumBits);
diff --git a/lib/Parse/DeclSpec.cpp b/lib/Parse/DeclSpec.cpp
index 8b3b2851c1..e58076ee5a 100644
--- a/lib/Parse/DeclSpec.cpp
+++ b/lib/Parse/DeclSpec.cpp
@@ -159,6 +159,8 @@ const char *DeclSpec::getSpecifierName(DeclSpec::TST T) {
case DeclSpec::TST_void: return "void";
case DeclSpec::TST_char: return "char";
case DeclSpec::TST_wchar: return "wchar_t";
+ case DeclSpec::TST_char16: return "char16_t";
+ case DeclSpec::TST_char32: return "char32_t";
case DeclSpec::TST_int: return "int";
case DeclSpec::TST_float: return "float";
case DeclSpec::TST_double: return "double";
diff --git a/lib/Parse/ParseDecl.cpp b/lib/Parse/ParseDecl.cpp
index 94855b24f5..cefd325248 100644
--- a/lib/Parse/ParseDecl.cpp
+++ b/lib/Parse/ParseDecl.cpp
@@ -159,6 +159,8 @@ AttributeList *Parser::ParseAttributes(SourceLocation *EndLoc) {
break;
case tok::kw_char:
case tok::kw_wchar_t:
+ case tok::kw_char16_t:
+ case tok::kw_char32_t:
case tok::kw_bool:
case tok::kw_short:
case tok::kw_int:
@@ -999,6 +1001,12 @@ void Parser::ParseDeclarationSpecifiers(DeclSpec &DS,
case tok::kw_wchar_t:
isInvalid = DS.SetTypeSpecType(DeclSpec::TST_wchar, Loc, PrevSpec);
break;
+ case tok::kw_char16_t:
+ isInvalid = DS.SetTypeSpecType(DeclSpec::TST_char16, Loc, PrevSpec);
+ break;
+ case tok::kw_char32_t:
+ isInvalid = DS.SetTypeSpecType(DeclSpec::TST_char32, Loc, PrevSpec);
+ break;
case tok::kw_bool:
case tok::kw__Bool:
isInvalid = DS.SetTypeSpecType(DeclSpec::TST_bool, Loc, PrevSpec);
@@ -1226,6 +1234,12 @@ bool Parser::ParseOptionalTypeSpecifier(DeclSpec &DS, int& isInvalid,
case tok::kw_wchar_t:
isInvalid = DS.SetTypeSpecType(DeclSpec::TST_wchar, Loc, PrevSpec);
break;
+ case tok::kw_char16_t:
+ isInvalid = DS.SetTypeSpecType(DeclSpec::TST_char16, Loc, PrevSpec);
+ break;
+ case tok::kw_char32_t:
+ isInvalid = DS.SetTypeSpecType(DeclSpec::TST_char32, Loc, PrevSpec);
+ break;
case tok::kw_bool:
case tok::kw__Bool:
isInvalid = DS.SetTypeSpecType(DeclSpec::TST_bool, Loc, PrevSpec);
@@ -1714,6 +1728,8 @@ bool Parser::isTypeSpecifierQualifier() {
case tok::kw_void:
case tok::kw_char:
case tok::kw_wchar_t:
+ case tok::kw_char16_t:
+ case tok::kw_char32_t:
case tok::kw_int:
case tok::kw_float:
case tok::kw_double:
@@ -1802,6 +1818,9 @@ bool Parser::isDeclarationSpecifier() {
case tok::kw_void:
case tok::kw_char:
case tok::kw_wchar_t:
+ case tok::kw_char16_t:
+ case tok::kw_char32_t:
+
case tok::kw_int:
case tok::kw_float:
case tok::kw_double:
diff --git a/lib/Parse/ParseExpr.cpp b/lib/Parse/ParseExpr.cpp
index cd7618f665..c2086b9e1a 100644
--- a/lib/Parse/ParseExpr.cpp
+++ b/lib/Parse/ParseExpr.cpp
@@ -739,6 +739,8 @@ Parser::OwningExprResult Parser::ParseCastExpression(bool isUnaryExpression,
case tok::kw_char:
case tok::kw_wchar_t:
+ case tok::kw_char16_t:
+ case tok::kw_char32_t:
case tok::kw_bool:
case tok::kw_short:
case tok::kw_int:
diff --git a/lib/Parse/ParseExprCXX.cpp b/lib/Parse/ParseExprCXX.cpp
index 1c00a8eabe..68101fcdf4 100644
--- a/lib/Parse/ParseExprCXX.cpp
+++ b/lib/Parse/ParseExprCXX.cpp
@@ -654,6 +654,12 @@ void Parser::ParseCXXSimpleTypeSpecifier(DeclSpec &DS) {
case tok::kw_wchar_t:
DS.SetTypeSpecType(DeclSpec::TST_wchar, Loc, PrevSpec);
break;
+ case tok::kw_char16_t:
+ DS.SetTypeSpecType(DeclSpec::TST_char16, Loc, PrevSpec);
+ break;
+ case tok::kw_char32_t:
+ DS.SetTypeSpecType(DeclSpec::TST_char32, Loc, PrevSpec);
+ break;
case tok::kw_bool:
DS.SetTypeSpecType(DeclSpec::TST_bool, Loc, PrevSpec);
break;
diff --git a/lib/Parse/ParseTentative.cpp b/lib/Parse/ParseTentative.cpp
index 02687a216c..97f6f526d4 100644
--- a/lib/Parse/ParseTentative.cpp
+++ b/lib/Parse/ParseTentative.cpp
@@ -681,6 +681,8 @@ Parser::TPResult Parser::isCXXDeclarationSpecifier() {
case tok::kw_char:
case tok::kw_wchar_t:
+ case tok::kw_char16_t:
+ case tok::kw_char32_t:
case tok::kw_bool:
case tok::kw_short:
case tok::kw_int:
diff --git a/lib/Sema/SemaOverload.cpp b/lib/Sema/SemaOverload.cpp
index b7f698eb0b..bee3936048 100644
--- a/lib/Sema/SemaOverload.cpp
+++ b/lib/Sema/SemaOverload.cpp
@@ -2792,7 +2792,8 @@ Sema::AddBuiltinOperatorCandidates(OverloadedOperatorKind Op,
LastPromotedArithmeticType = 16;
const unsigned NumArithmeticTypes = 16;
QualType ArithmeticTypes[NumArithmeticTypes] = {
- Context.BoolTy, Context.CharTy, Context.WCharTy,
+ Context.BoolTy, Context.CharTy, Context.WCharTy,
+// Context.Char16Ty, Context.Char32Ty,
Context.SignedCharTy, Context.ShortTy,
Context.UnsignedCharTy, Context.UnsignedShortTy,
Context.IntTy, Context.LongTy, Context.LongLongTy,
diff --git a/lib/Sema/SemaType.cpp b/lib/Sema/SemaType.cpp
index 7551d93c66..8195aba967 100644
--- a/lib/Sema/SemaType.cpp
+++ b/lib/Sema/SemaType.cpp
@@ -88,6 +88,16 @@ QualType Sema::ConvertDeclSpecToType(const DeclSpec &DS,
Result = Context.getUnsignedWCharType();
}
break;
+ case DeclSpec::TST_char16:
+ assert(DS.getTypeSpecSign() == DeclSpec::TSS_unspecified &&
+ "Unknown TSS value");
+ Result = Context.Char16Ty;
+ break;
+ case DeclSpec::TST_char32:
+ assert(DS.getTypeSpecSign() == DeclSpec::TSS_unspecified &&
+ "Unknown TSS value");
+ Result = Context.Char32Ty;
+ break;
case DeclSpec::TST_unspecified:
// "<proto1,proto2>" is an objc qualified ID with a missing id.
if (DeclSpec::ProtocolQualifierListTy PQ = DS.getProtocolQualifiers()) {