Mercurial > projects > ldc
diff dmd2/mangle.c @ 1452:638d16625da2
LDC 2 compiles again.
author | Robert Clipsham <robert@octarineparrot.com> |
---|---|
date | Sat, 30 May 2009 17:23:32 +0100 |
parents | f04dde6e882c |
children | 54b3c1394d62 |
line wrap: on
line diff
--- a/dmd2/mangle.c Thu May 28 00:07:21 2009 +0200 +++ b/dmd2/mangle.c Sat May 30 17:23:32 2009 +0100 @@ -1,291 +1,298 @@ - -// Compiler implementation of the D programming language -// Copyright (c) 1999-2007 by Digital Mars -// All Rights Reserved -// written by Walter Bright -// http://www.digitalmars.com -// License for redistribution is by either the Artistic License -// in artistic.txt, or the GNU General Public License in gnu.txt. -// See the included readme.txt for details. - -#include <stdio.h> -#include <string.h> -#include <ctype.h> -#include <assert.h> - -#include "root.h" - -#include "init.h" -#include "declaration.h" -#include "aggregate.h" -#include "mtype.h" -#include "attrib.h" -#include "template.h" -#include "id.h" -#include "module.h" - -#if TARGET_LINUX -char *cpp_mangle(Dsymbol *s); -#endif - -char *mangle(Declaration *sthis) -{ - OutBuffer buf; - char *id; - Dsymbol *s; - - //printf("::mangle(%s)\n", sthis->toChars()); - s = sthis; - do - { - //printf("mangle: s = %p, '%s', parent = %p\n", s, s->toChars(), s->parent); - if (s->ident) - { - FuncDeclaration *fd = s->isFuncDeclaration(); - if (s != sthis && fd) - { - id = mangle(fd); - buf.prependstring(id); - goto L1; - } - else - { - id = s->ident->toChars(); - int len = strlen(id); - char tmp[sizeof(len) * 3 + 1]; - buf.prependstring(id); - sprintf(tmp, "%d", len); - buf.prependstring(tmp); - } - } - else - buf.prependstring("0"); - s = s->parent; - } while (s); - -// buf.prependstring("_D"); -L1: - //printf("deco = '%s'\n", sthis->type->deco ? sthis->type->deco : "null"); - //printf("sthis->type = %s\n", sthis->type->toChars()); - FuncDeclaration *fd = sthis->isFuncDeclaration(); - if (fd && (fd->needThis() || fd->isNested())) - buf.writeByte(Type::needThisPrefix()); - if (sthis->type->deco) - buf.writestring(sthis->type->deco); - else - { assert(fd->inferRetType); - } - - id = buf.toChars(); - buf.data = NULL; - return id; -} - -char *Declaration::mangle() -#if __DMC__ - __out(result) - { - int len = strlen(result); - - assert(len > 0); - //printf("mangle: '%s' => '%s'\n", toChars(), result); - for (int i = 0; i < len; i++) - { - assert(result[i] == '_' || - result[i] == '@' || - isalnum(result[i]) || result[i] & 0x80); - } - } - __body -#endif - { - //printf("Declaration::mangle(this = %p, '%s', parent = '%s', linkage = %d)\n", this, toChars(), parent ? parent->toChars() : "null", linkage); - if (!parent || parent->isModule() || linkage == LINKcpp) // if at global scope - { - // If it's not a D declaration, no mangling - switch (linkage) - { - case LINKd: - break; - - // LDC - case LINKintrinsic: - - case LINKc: - case LINKwindows: - case LINKpascal: - return ident->toChars(); - - case LINKcpp: -#if TARGET_LINUX - return cpp_mangle(this); -#else - // Windows C++ mangling is done by C++ back end - return ident->toChars(); -#endif - - case LINKdefault: - error("forward declaration"); - return ident->toChars(); - - default: - fprintf(stdmsg, "'%s', linkage = %d\n", toChars(), linkage); - assert(0); - } - } - char *p = ::mangle(this); - OutBuffer buf; - buf.writestring("_D"); - buf.writestring(p); - p = buf.toChars(); - buf.data = NULL; - //printf("Declaration::mangle(this = %p, '%s', parent = '%s', linkage = %d) = %s\n", this, toChars(), parent ? parent->toChars() : "null", linkage, p); - return p; - } - -char *FuncDeclaration::mangle() -#if __DMC__ - __out(result) - { - assert(strlen(result) > 0); - } - __body -#endif - { - if (isMain()) - return (char *)"_Dmain"; - - if (isWinMain() || isDllMain()) - return ident->toChars(); - - assert(this); - return Declaration::mangle(); - } - - -char *StructDeclaration::mangle() -{ - //printf("StructDeclaration::mangle() '%s'\n", toChars()); - return Dsymbol::mangle(); -} - - -char *TypedefDeclaration::mangle() -{ - //printf("TypedefDeclaration::mangle() '%s'\n", toChars()); - return Dsymbol::mangle(); -} - - -char *ClassDeclaration::mangle() -{ - Dsymbol *parentsave = parent; - - //printf("ClassDeclaration::mangle() %s.%s\n", parent->toChars(), toChars()); - - /* These are reserved to the compiler, so keep simple - * names for them. - */ - if (ident == Id::Exception) - { if (parent->ident == Id::object) - parent = NULL; - } - else if (ident == Id::TypeInfo || -// ident == Id::Exception || - ident == Id::TypeInfo_Struct || - ident == Id::TypeInfo_Class || - ident == Id::TypeInfo_Typedef || - ident == Id::TypeInfo_Tuple || - this == object || - this == classinfo || - this == Module::moduleinfo || - memcmp(ident->toChars(), "TypeInfo_", 9) == 0 - ) - parent = NULL; - - char *id = Dsymbol::mangle(); - parent = parentsave; - return id; -} - - -char *TemplateInstance::mangle() -{ - OutBuffer buf; - char *id; - -#if 0 - printf("TemplateInstance::mangle() %s", toChars()); - if (parent) - printf(" parent = %s %s", parent->kind(), parent->toChars()); - printf("\n"); -#endif - id = ident ? ident->toChars() : toChars(); - if (tempdecl->parent) - { - char *p = tempdecl->parent->mangle(); - if (p[0] == '_' && p[1] == 'D') - p += 2; - buf.writestring(p); - } - buf.printf("%"PRIuSIZE"%s", strlen(id), id); - id = buf.toChars(); - buf.data = NULL; - //printf("TemplateInstance::mangle() %s = %s\n", toChars(), id); - return id; -} - - -char *TemplateMixin::mangle() -{ - OutBuffer buf; - char *id; - -#if 0 - printf("TemplateMixin::mangle() %s", toChars()); - if (parent) - printf(" parent = %s %s", parent->kind(), parent->toChars()); - printf("\n"); -#endif - id = ident ? ident->toChars() : toChars(); - if (parent) - { - char *p = parent->mangle(); - if (p[0] == '_' && p[1] == 'D') - p += 2; - buf.writestring(p); - } - buf.printf("%"PRIuSIZE"%s", strlen(id), id); - id = buf.toChars(); - buf.data = NULL; - //printf("TemplateMixin::mangle() %s = %s\n", toChars(), id); - return id; -} - -char *Dsymbol::mangle() -{ - OutBuffer buf; - char *id; - -#if 0 - printf("Dsymbol::mangle() '%s'", toChars()); - if (parent) - printf(" parent = %s %s", parent->kind(), parent->toChars()); - printf("\n"); -#endif - id = ident ? ident->toChars() : toChars(); - if (parent) - { - char *p = parent->mangle(); - if (p[0] == '_' && p[1] == 'D') - p += 2; - buf.writestring(p); - } - buf.printf("%"PRIuSIZE"%s", strlen(id), id); - id = buf.toChars(); - buf.data = NULL; - //printf("Dsymbol::mangle() %s = %s\n", toChars(), id); - return id; -} - - + +// Compiler implementation of the D programming language +// Copyright (c) 1999-2009 by Digital Mars +// All Rights Reserved +// written by Walter Bright +// http://www.digitalmars.com +// License for redistribution is by either the Artistic License +// in artistic.txt, or the GNU General Public License in gnu.txt. +// See the included readme.txt for details. + +#include <stdio.h> +#include <string.h> +#include <ctype.h> +#include <assert.h> + +#include "root.h" + +#include "init.h" +#include "declaration.h" +#include "aggregate.h" +#include "mtype.h" +#include "attrib.h" +#include "template.h" +#include "id.h" +#include "module.h" + +#if TARGET_LINUX || TARGET_OSX || TARGET_FREEBSD || TARGET_SOLARIS +char *cpp_mangle(Dsymbol *s); +#endif + +char *mangle(Declaration *sthis) +{ + OutBuffer buf; + char *id; + Dsymbol *s; + + //printf("::mangle(%s)\n", sthis->toChars()); + s = sthis; + do + { + //printf("mangle: s = %p, '%s', parent = %p\n", s, s->toChars(), s->parent); + if (s->ident) + { + FuncDeclaration *fd = s->isFuncDeclaration(); + if (s != sthis && fd) + { + id = mangle(fd); + buf.prependstring(id); + goto L1; + } + else + { + id = s->ident->toChars(); + int len = strlen(id); + char tmp[sizeof(len) * 3 + 1]; + buf.prependstring(id); + sprintf(tmp, "%d", len); + buf.prependstring(tmp); + } + } + else + buf.prependstring("0"); + s = s->parent; + } while (s); + +// buf.prependstring("_D"); +L1: + //printf("deco = '%s'\n", sthis->type->deco ? sthis->type->deco : "null"); + //printf("sthis->type = %s\n", sthis->type->toChars()); + FuncDeclaration *fd = sthis->isFuncDeclaration(); + if (fd && (fd->needThis() || fd->isNested())) + buf.writeByte(Type::needThisPrefix()); + if (sthis->type->deco) + buf.writestring(sthis->type->deco); + else + { +#ifdef DEBUG + if (!fd->inferRetType) + printf("%s\n", fd->toChars()); +#endif + assert(fd->inferRetType); + } + + id = buf.toChars(); + buf.data = NULL; + return id; +} + +char *Declaration::mangle() +#if __DMC__ + __out(result) + { + int len = strlen(result); + + assert(len > 0); + //printf("mangle: '%s' => '%s'\n", toChars(), result); + for (int i = 0; i < len; i++) + { + assert(result[i] == '_' || + result[i] == '@' || + isalnum(result[i]) || result[i] & 0x80); + } + } + __body +#endif + { + //printf("Declaration::mangle(this = %p, '%s', parent = '%s', linkage = %d)\n", this, toChars(), parent ? parent->toChars() : "null", linkage); + if (!parent || parent->isModule() || linkage == LINKcpp) // if at global scope + { + // If it's not a D declaration, no mangling + switch (linkage) + { + case LINKd: + break; + + // LDC + case LINKintrinsic: + + case LINKc: + case LINKwindows: + case LINKpascal: + return ident->toChars(); + + case LINKcpp: +#if DMDV2 && (TARGET_LINUX || TARGET_OSX || TARGET_FREEBSD || TARGET_SOLARIS) + return cpp_mangle(this); +#else + // Windows C++ mangling is done by C++ back end + return ident->toChars(); +#endif + + case LINKdefault: + error("forward declaration"); + return ident->toChars(); + + default: + fprintf(stdmsg, "'%s', linkage = %d\n", toChars(), linkage); + assert(0); + } + } + char *p = ::mangle(this); + OutBuffer buf; + buf.writestring("_D"); + buf.writestring(p); + p = buf.toChars(); + buf.data = NULL; + //printf("Declaration::mangle(this = %p, '%s', parent = '%s', linkage = %d) = %s\n", this, toChars(), parent ? parent->toChars() : "null", linkage, p); + return p; + } + +char *FuncDeclaration::mangle() +#if __DMC__ + __out(result) + { + assert(strlen(result) > 0); + } + __body +#endif + { + if (isMain()) + return (char *)"_Dmain"; + + if (isWinMain() || isDllMain() || ident == Id::tls_get_addr) + return ident->toChars(); + + assert(this); + return Declaration::mangle(); + } + +char *StructDeclaration::mangle() +{ + //printf("StructDeclaration::mangle() '%s'\n", toChars()); + return Dsymbol::mangle(); +} + + +char *TypedefDeclaration::mangle() +{ + //printf("TypedefDeclaration::mangle() '%s'\n", toChars()); + return Dsymbol::mangle(); +} + + +char *ClassDeclaration::mangle() +{ + Dsymbol *parentsave = parent; + + //printf("ClassDeclaration::mangle() %s.%s\n", parent->toChars(), toChars()); + + /* These are reserved to the compiler, so keep simple + * names for them. + */ + if (ident == Id::Exception) + { if (parent->ident == Id::object) + parent = NULL; + } + else if (ident == Id::TypeInfo || +// ident == Id::Exception || + ident == Id::TypeInfo_Struct || + ident == Id::TypeInfo_Class || + ident == Id::TypeInfo_Typedef || + ident == Id::TypeInfo_Tuple || + this == object || + this == classinfo || + this == Module::moduleinfo || + memcmp(ident->toChars(), "TypeInfo_", 9) == 0 + ) + parent = NULL; + + char *id = Dsymbol::mangle(); + parent = parentsave; + return id; +} + + +char *TemplateInstance::mangle() +{ + OutBuffer buf; + char *id; + +#if 0 + printf("TemplateInstance::mangle() %s", toChars()); + if (parent) + printf(" parent = %s %s", parent->kind(), parent->toChars()); + printf("\n"); +#endif + id = ident ? ident->toChars() : toChars(); + if (!tempdecl) + error("is not defined"); + else if (tempdecl->parent) + { + char *p = tempdecl->parent->mangle(); + if (p[0] == '_' && p[1] == 'D') + p += 2; + buf.writestring(p); + } + buf.printf("%zu%s", strlen(id), id); + id = buf.toChars(); + buf.data = NULL; + //printf("TemplateInstance::mangle() %s = %s\n", toChars(), id); + return id; +} + +#if IN_LLVM +char *TemplateMixin::mangle() +{ + OutBuffer buf; + char *id; + +#if 0 + printf("TemplateMixin::mangle() %s", toChars()); + if (parent) + printf(" parent = %s %s", parent->kind(), parent->toChars()); + printf("\n"); +#endif + id = ident ? ident->toChars() : toChars(); + if (parent) + { + char *p = parent->mangle(); + if (p[0] == '_' && p[1] == 'D') + p += 2; + buf.writestring(p); + } + buf.printf("%zu%s", strlen(id), id); + id = buf.toChars(); + buf.data = NULL; + //printf("TemplateMixin::mangle() %s = %s\n", toChars(), id); + return id; +} +#endif + +char *Dsymbol::mangle() +{ + OutBuffer buf; + char *id; + +#if 0 + printf("Dsymbol::mangle() '%s'", toChars()); + if (parent) + printf(" parent = %s %s", parent->kind(), parent->toChars()); + printf("\n"); +#endif + id = ident ? ident->toChars() : toChars(); + if (parent) + { + char *p = parent->mangle(); + if (p[0] == '_' && p[1] == 'D') + p += 2; + buf.writestring(p); + } + buf.printf("%zu%s", strlen(id), id); + id = buf.toChars(); + buf.data = NULL; + //printf("Dsymbol::mangle() %s = %s\n", toChars(), id); + return id; +} + +