| //===---------------------------------------------------------------------===// |
| // Random Notes |
| //===---------------------------------------------------------------------===// |
| |
| C90/C99/C++ Comparisons: |
| http://david.tribble.com/text/cdiffs.htm |
| |
| //===---------------------------------------------------------------------===// |
| |
| To time GCC preprocessing speed without output, use: |
| "time gcc -MM file" |
| This is similar to -Eonly. |
| |
| |
| //===---------------------------------------------------------------------===// |
| |
| C++ Template Instantiation benchmark: |
| http://users.rcn.com/abrahams/instantiation_speed/index.html |
| |
| //===---------------------------------------------------------------------===// |
| |
| TODO: File Manager Speedup: |
| |
| We currently do a lot of stat'ing for files that don't exist, particularly |
| when lots of -I paths exist (e.g. see the <iostream> example, check for |
| failures in stat in FileManager::getFile). It would be far better to make |
| the following changes: |
| 1. FileEntry contains a sys::Path instead of a std::string for Name. |
| 2. sys::Path contains timestamp and size, lazily computed. Eliminate from |
| FileEntry. |
| 3. File UIDs are created on request, not when files are opened. |
| These changes make it possible to efficiently have FileEntry objects for |
| files that exist on the file system, but have not been used yet. |
| |
| Once this is done: |
| 1. DirectoryEntry gets a boolean value "has read entries". When false, not |
| all entries in the directory are in the file mgr, when true, they are. |
| 2. Instead of stat'ing the file in FileManager::getFile, check to see if |
| the dir has been read. If so, fail immediately, if not, read the dir, |
| then retry. |
| 3. Reading the dir uses the getdirentries syscall, creating an FileEntry |
| for all files found. |
| |
| //===---------------------------------------------------------------------===// |
| |
| TODO: Fast #Import: |
| |
| * Get frameworks that don't use #import to do so, e.g. |
| DirectoryService, AudioToolbox, CoreFoundation, etc. Why not using #import? |
| Because they work in C mode? C has #import. |
| * Have the lexer return a token for #import instead of handling it itself. |
| - Create a new preprocessor object with no external state (no -D/U options |
| from the command line, etc). Alternatively, keep track of exactly which |
| external state is used by a #import: declare it somehow. |
| * When having reading a #import file, keep track of whether we have (and/or |
| which) seen any "configuration" macros. Various cases: |
| - Uses of target args (__POWERPC__, __i386): Header has to be parsed |
| multiple times, per-target. What about #ifndef checks? How do we know? |
| - "Configuration" preprocessor macros not defined: POWERPC, etc. What about |
| things like __STDC__ etc? What is and what isn't allowed. |
| * Special handling for "umbrella" headers, which just contain #import stmts: |
| - Cocoa.h/AppKit.h - Contain pointers to digests instead of entire digests |
| themselves? Foundation.h isn't pure umbrella! |
| * Frameworks digests: |
| - Can put "digest" of a framework-worth of headers into the framework |
| itself. To open AppKit, just mmap |
| /System/Library/Frameworks/AppKit.framework/"digest", which provides a |
| symbol table in a well defined format. Lazily unstream stuff that is |
| needed. Contains declarations, macros, and debug information. |
| - System frameworks ship with digests. How do we handle configuration |
| information? How do we handle stuff like: |
| #if MAC_OS_X_VERSION_MAX_ALLOWED >= MAC_OS_X_VERSION_10_2 |
| which guards a bunch of decls? Should there be a couple of default |
| configs, then have the UI fall back to building/caching its own? |
| - GUI automatically builds digests when UI is idle, both of system |
| frameworks if they aren't not available in the right config, and of app |
| frameworks. |
| - GUI builds dependence graph of frameworks/digests based on #imports. If a |
| digest is out date, dependent digests are automatically invalidated. |
| |
| * New constraints on #import for objc-v3: |
| - #imported file must not define non-inline function bodies. |
| - Alternatively, they can, and these bodies get compiled/linked *once* |
| per app into a dylib. What about building user dylibs? |
| - Restrictions on ObjC grammar: can't #import the body of a for stmt or fn. |
| - Compiler must detect and reject these cases. |
| - #defines defined within a #import have two behaviors: |
| - By default, they escape the header. These macros *cannot* be #undef'd |
| by other code: this is enforced by the front-end. |
| - Optionally, user can specify what macros escape (whitelist) or can use |
| #undef. |
| |
| //===---------------------------------------------------------------------===// |
| |
| TODO: New language feature: Configuration queries: |
| - Instead of #ifdef __POWERPC__, use "if (strcmp(`cpu`, __POWERPC__))", or |
| some other, better, syntax. |
| - Use it to increase the number of "architecture-clean" #import'd files, |
| allowing a single index to be used for all fat slices. |
| |
| //===---------------------------------------------------------------------===// |
| // Specifying targets: -triple and -arch |
| ===---------------------------------------------------------------------===// |
| |
| The clang supports "-triple" and "-arch" options. At most one -triple option may |
| be specified, while multiple -arch options can be specified. Both are optional. |
| |
| The "selection of target" behavior is defined as follows: |
| |
| (1) If the user does not specify -triple: |
| |
| (a) If no -arch options are specified, the target triple used is the host |
| triple (in llvm/Config/config.h). |
| |
| (b) If one or more -arch's are specified (and no -triple), then there is |
| one triple for each -arch, where the specified arch is substituted |
| for the arch in the host triple. Example: |
| |
| host triple = i686-apple-darwin9 |
| command: clang -arch ppc -arch ppc64 ... |
| triples used: ppc-apple-darwin9 ppc64-apple-darwin9 |
| |
| (2) The user does specify a -triple (only one allowed): |
| |
| (a) If no -arch options are specified, the triple specified by -triple |
| is used. E.g clang -triple i686-apple-darwin9 |
| |
| (b) If one or more -arch options are specified, then the triple specified |
| by -triple is used as the primary target, and the arch's specified |
| by -arch are used to create secondary targets. For example: |
| |
| clang -triple i686-apple-darwin9 -arch ppc -arch ppc64 |
| |
| has the following targets: |
| |
| i686-apple-darwin9 (primary target) |
| ppc-apple-darwin9 (secondary target) |
| ppc64-apple-darwin9 (secondary target) |
| |
| The secondary targets are used in the 'portability' model (see below). |