diff --git a/lib/CodeGen/CGExprScalar.cpp b/lib/CodeGen/CGExprScalar.cpp
index fc8639d..622d2c5 100644
--- a/lib/CodeGen/CGExprScalar.cpp
+++ b/lib/CodeGen/CGExprScalar.cpp
@@ -495,7 +495,7 @@
   llvm::Constant *Selector = CGF.CGM.GetAddrOfConstantString(SelStr);
 
   llvm::Value *SelPtr = Builder.CreateStructGEP(Selector, 0);
-  return Runtime->generateMessageSend(Builder, ConvertType(E->getType()),
+  return Runtime->GenerateMessageSend(Builder, ConvertType(E->getType()),
                                       CGF.LoadObjCSelf(),
                                       Receiver, SelPtr,
                                       &Args[0], Args.size());
diff --git a/lib/CodeGen/CGObjCEtoile.cpp b/lib/CodeGen/CGObjCEtoile.cpp
index d5023b4..94471ad 100644
--- a/lib/CodeGen/CGObjCEtoile.cpp
+++ b/lib/CodeGen/CGObjCEtoile.cpp
@@ -46,10 +46,15 @@
   llvm::Value *getSelector(llvm::IRBuilder &Builder,
       llvm::Value *SelName,
       llvm::Value *SelTypes);
-  virtual llvm::Function *MethodPreamble(const llvm::Type *ReturnTy,
+  virtual llvm::Function *MethodPreamble(
+                                         const std::string &ClassName,
+                                         const std::string &CategoryName,
+                                         const std::string &MethodName,
+                                         const llvm::Type *ReturnTy,
                                          const llvm::Type *SelfTy,
                                          const llvm::Type **ArgTy,
                                          unsigned ArgC,
+                                         bool isClassMethod,
                                          bool isVarArg);
 };
 } // end anonymous namespace
@@ -207,10 +212,14 @@
 /// Generates an LLVM Function object corresponding to the Objective-C method,
 /// including the implicit arguments.
 llvm::Function *CGObjCEtoile::MethodPreamble(
+                                         const std::string &ClassName,
+                                         const std::string &CategoryName,
+                                         const std::string &MethodName,
                                          const llvm::Type *ReturnTy,
                                          const llvm::Type *SelfTy,
                                          const llvm::Type **ArgTy,
                                          unsigned ArgC,
+                                         bool isClassMethod,
                                          bool isVarArg) {
   std::vector<const llvm::Type*> Args;
   //Args.push_back(SelfTy);
diff --git a/lib/CodeGen/CGObjCGNU.cpp b/lib/CodeGen/CGObjCGNU.cpp
index 8373cfd..ad38d9a 100644
--- a/lib/CodeGen/CGObjCGNU.cpp
+++ b/lib/CodeGen/CGObjCGNU.cpp
@@ -1,4 +1,4 @@
-//===------- CGObjCGNU.cpp - Emit LLVM Code from ASTs for a Module --------===// 
+//===------- CGObjCGNU.cpp - Emit LLVM Code from ASTs for a Module --------===//
 //
 //                     The LLVM Compiler Infrastructure
 //
@@ -7,7 +7,10 @@
 //
 //===----------------------------------------------------------------------===//
 //
-// This provides Objective-C code generation targetting the GNU runtime.
+// This provides Objective-C code generation targetting the GNU runtime.  The
+// class in this file generates structures used by the GNU Objective-C runtime
+// library.  These structures are defined in objc/objc.h and objc/objc-api.h in
+// the GNU runtime distribution.
 //
 //===----------------------------------------------------------------------===//
 
@@ -16,11 +19,21 @@
 #include "llvm/Support/Compiler.h"
 #include "llvm/Support/IRBuilder.h"
 #include "llvm/ADT/SmallVector.h"
+#include "llvm/ADT/StringMap.h"
+#include <map>
+
+using llvm::dyn_cast;
+
+// The version of the runtime that this class targets.  Must match the version
+// in the runtime.
+static const int RuntimeVersion = 8;
+static const int ProtocolVersion = 2;
 
 namespace {
 class CGObjCGNU : public clang::CodeGen::CGObjCRuntime {
 private:
   llvm::Module &TheModule;
+  const llvm::StructType *SelStructTy;
   const llvm::Type *SelectorTy;
   const llvm::Type *PtrToInt8Ty;
   const llvm::Type *IMPTy;
@@ -29,28 +42,127 @@
   const llvm::Type *PtrTy;
   const llvm::Type *LongTy;
   const llvm::Type *PtrToIntTy;
+  std::vector<llvm::Constant*> Classes;
+  std::vector<llvm::Constant*> Categories;
+  std::vector<llvm::Constant*> ConstantStrings;
+  llvm::Function *LoadFunction;
+  llvm::StringMap<llvm::Constant*> ExistingProtocols;
+  typedef std::pair<std::string, std::string> TypedSelector;
+  std::map<TypedSelector, llvm::GlobalAlias*> TypedSelectors;
+  llvm::StringMap<llvm::GlobalAlias*> UntypedSelectors;
+  // Some zeros used for GEPs in lots of places.
+  llvm::Constant *Zeros[2];
+  llvm::Constant *NULLPtr;
+private:
+  llvm::Constant *GenerateIvarList(
+      const llvm::SmallVectorImpl<llvm::Constant *>  &IvarNames,
+      const llvm::SmallVectorImpl<llvm::Constant *>  &IvarTypes,
+      const llvm::SmallVectorImpl<llvm::Constant *>  &IvarOffsets);
+  llvm::Constant *GenerateMethodList(const std::string &ClassName,
+      const std::string &CategoryName,
+      const llvm::SmallVectorImpl<llvm::Constant *>  &MethodNames, 
+      const llvm::SmallVectorImpl<llvm::Constant *>  &MethodTypes, 
+      bool isClassMethodList);
+  llvm::Constant *GenerateProtocolList(
+      const llvm::SmallVectorImpl<std::string> &Protocols);
+  llvm::Constant *GenerateClassStructure(
+      llvm::Constant *MetaClass,
+      llvm::Constant *SuperClass,
+      unsigned info,
+      llvm::Constant *Name,
+      llvm::Constant *Version,
+      llvm::Constant *InstanceSize,
+      llvm::Constant *IVars,
+      llvm::Constant *Methods,
+      llvm::Constant *Protocols);
+  llvm::Constant *GenerateProtocolMethodList(
+      const llvm::SmallVectorImpl<llvm::Constant *>  &MethodNames,
+      const llvm::SmallVectorImpl<llvm::Constant *>  &MethodTypes);
+  llvm::Constant *MakeConstantString(const std::string &Str, const std::string
+      &Name="");
+  llvm::Constant *MakeGlobal(const llvm::StructType *Ty,
+      std::vector<llvm::Constant*> &V, const std::string &Name="");
+  llvm::Constant *MakeGlobal(const llvm::ArrayType *Ty,
+      std::vector<llvm::Constant*> &V, const std::string &Name="");
 public:
   CGObjCGNU(llvm::Module &Mp,
     const llvm::Type *LLVMIntType,
     const llvm::Type *LLVMLongType);
-  virtual llvm::Value *generateMessageSend(llvm::IRBuilder &Builder,
+  virtual llvm::Constant *GenerateConstantString(const char *String, 
+      const size_t length);
+  virtual llvm::Value *GenerateMessageSend(llvm::IRBuilder &Builder,
                                            const llvm::Type *ReturnTy,
                                            llvm::Value *Sender,
                                            llvm::Value *Receiver,
                                            llvm::Value *Selector,
                                            llvm::Value** ArgV,
                                            unsigned ArgC);
-  llvm::Value *getSelector(llvm::IRBuilder &Builder,
+  virtual llvm::Value *GenerateMessageSendSuper(llvm::IRBuilder &Builder,
+                                            const llvm::Type *ReturnTy,
+                                            llvm::Value *Sender,
+                                            const char *SuperClassName,
+                                            llvm::Value *Receiver,
+                                            llvm::Value *Selector,
+                                            llvm::Value** ArgV,
+                                            unsigned ArgC);
+  virtual llvm::Value *LookupClass(llvm::IRBuilder &Builder, llvm::Value
+      *ClassName);
+  virtual llvm::Value *GetSelector(llvm::IRBuilder &Builder,
       llvm::Value *SelName,
       llvm::Value *SelTypes);
-  virtual llvm::Function *MethodPreamble(const llvm::Type *ReturnTy,
-                                 const llvm::Type *SelfTy,
-                                 const llvm::Type **ArgTy,
-                                 unsigned ArgC,
-                                 bool isVarArg);
+  virtual llvm::Function *MethodPreamble(
+                                         const std::string &ClassName,
+                                         const std::string &CategoryName,
+                                         const std::string &MethodName,
+                                         const llvm::Type *ReturnTy,
+                                         const llvm::Type *SelfTy,
+                                         const llvm::Type **ArgTy,
+                                         unsigned ArgC,
+                                         bool isClassMethod,
+                                         bool isVarArg);
+  virtual void GenerateCategory(const char *ClassName, const char *CategoryName,
+           const llvm::SmallVectorImpl<llvm::Constant *>  &InstanceMethodNames,
+           const llvm::SmallVectorImpl<llvm::Constant *>  &InstanceMethodTypes,
+           const llvm::SmallVectorImpl<llvm::Constant *>  &ClassMethodNames,
+           const llvm::SmallVectorImpl<llvm::Constant *>  &ClassMethodTypes,
+           const llvm::SmallVectorImpl<std::string> &Protocols);
+  virtual void GenerateClass(
+           const char *ClassName,
+           const char *SuperClassName,
+           const int instanceSize,
+           const llvm::SmallVectorImpl<llvm::Constant *>  &IvarNames,
+           const llvm::SmallVectorImpl<llvm::Constant *>  &IvarTypes,
+           const llvm::SmallVectorImpl<llvm::Constant *>  &IvarOffsets,
+           const llvm::SmallVectorImpl<llvm::Constant *>  &InstanceMethodNames,
+           const llvm::SmallVectorImpl<llvm::Constant *>  &InstanceMethodTypes,
+           const llvm::SmallVectorImpl<llvm::Constant *>  &ClassMethodNames,
+           const llvm::SmallVectorImpl<llvm::Constant *>  &ClassMethodTypes,
+           const llvm::SmallVectorImpl<std::string> &Protocols);
+  virtual llvm::Value *GenerateProtocolRef(llvm::IRBuilder &Builder, const char
+      *ProtocolName);
+  virtual void GenerateProtocol(const char *ProtocolName,
+      const llvm::SmallVectorImpl<std::string> &Protocols,
+      const llvm::SmallVectorImpl<llvm::Constant *>  &InstanceMethodNames,
+      const llvm::SmallVectorImpl<llvm::Constant *>  &InstanceMethodTypes,
+      const llvm::SmallVectorImpl<llvm::Constant *>  &ClassMethodNames,
+      const llvm::SmallVectorImpl<llvm::Constant *>  &ClassMethodTypes);
+  virtual llvm::Function *ModuleInitFunction();
 };
 } // end anonymous namespace
 
+
+
+static std::string SymbolNameForClass(const std::string &ClassName) {
+  return ".objc_class_" + ClassName;
+}
+
+static std::string SymbolNameForMethod(const std::string &ClassName, const
+  std::string &CategoryName, const std::string &MethodName, bool isClassMethod)
+{
+  return "._objc_method_" + ClassName +"("+CategoryName+")"+
+            (isClassMethod ? "+" : "-") + MethodName;
+}
+
 CGObjCGNU::CGObjCGNU(llvm::Module &M,
     const llvm::Type *LLVMIntType,
     const llvm::Type *LLVMLongType) : 
@@ -58,15 +170,20 @@
   IntTy(LLVMIntType),
   LongTy(LLVMLongType)
 {
+  Zeros[0] = llvm::ConstantInt::get(llvm::Type::Int32Ty, 0);
+  Zeros[1] = Zeros[0];
+  NULLPtr = llvm::ConstantPointerNull::get(
+    llvm::PointerType::getUnqual(llvm::Type::Int8Ty));
   // C string type.  Used in lots of places.
   PtrToInt8Ty = 
     llvm::PointerType::getUnqual(llvm::Type::Int8Ty);
   // Get the selector Type.
-  const llvm::Type *SelStructTy = llvm::StructType::get(
+  SelStructTy = llvm::StructType::get(
       PtrToInt8Ty,
       PtrToInt8Ty,
       NULL);
   SelectorTy = llvm::PointerType::getUnqual(SelStructTy);
+  M.addTypeName(".objc_selector", SelectorTy);
   PtrToIntTy = llvm::PointerType::getUnqual(IntTy);
   PtrTy = PtrToInt8Ty;
  
@@ -77,24 +194,67 @@
   llvm::cast<llvm::OpaqueType>(OpaqueObjTy.get())->refineAbstractTypeTo(IdTy);
   IdTy = llvm::cast<llvm::StructType>(OpaqueObjTy.get());
   IdTy = llvm::PointerType::getUnqual(IdTy);
+  M.addTypeName(".objc_id", IdTy);
  
   // IMP type
   std::vector<const llvm::Type*> IMPArgs;
   IMPArgs.push_back(IdTy);
   IMPArgs.push_back(SelectorTy);
   IMPTy = llvm::FunctionType::get(IdTy, IMPArgs, true);
-
+  M.addTypeName(".objc_imp", IMPTy);
+}
+// This has to perform the lookup every time, since posing and related
+// techniques can modify the name -> class mapping.
+llvm::Value *CGObjCGNU::LookupClass(llvm::IRBuilder &Builder,
+    llvm::Value *ClassName) {
+  llvm::Constant *ClassLookupFn =
+    TheModule.getOrInsertFunction("objc_lookup_class", IdTy, PtrToInt8Ty,
+        NULL);
+  return Builder.CreateCall(ClassLookupFn, ClassName);
 }
 
 /// Looks up the selector for the specified name / type pair.
 // FIXME: Selectors should be statically cached, not looked up on every call.
-llvm::Value *CGObjCGNU::getSelector(llvm::IRBuilder &Builder,
+llvm::Value *CGObjCGNU::GetSelector(llvm::IRBuilder &Builder,
     llvm::Value *SelName,
-    llvm::Value *SelTypes)
-{
-  // Look up the selector.
+    llvm::Value *SelTypes) {
+  // For static selectors, we return an alias for now then store them all in a
+  // list that the runtime will initialise later.
+  if (llvm::Constant *CName = dyn_cast<llvm::Constant>(SelName)) {
+    // Untyped selector
+    if (SelTypes == 0) {
+      // If it's already cached, return it.
+      if (UntypedSelectors[CName->getStringValue()]) {
+        return Builder.CreateLoad(UntypedSelectors[CName->getStringValue()]);
+      }
+      // If it isn't, cache it.
+      llvm::GlobalAlias *Sel = new llvm::GlobalAlias(
+          llvm::PointerType::getUnqual(SelectorTy),
+          llvm::GlobalValue::InternalLinkage, ".objc_untyped_selector_alias",
+          NULL, &TheModule);
+      UntypedSelectors[CName->getStringValue()] = Sel;
+      return Builder.CreateLoad(Sel);
+    }
+    // Typed selectors
+    if (llvm::Constant *CTypes = dyn_cast<llvm::Constant>(SelTypes)) {
+      TypedSelector Selector = TypedSelector(CName->getStringValue(),
+          CTypes->getStringValue());
+      // If it's already cached, return it.
+      if (TypedSelectors[Selector]) {
+        return Builder.CreateLoad(TypedSelectors[Selector]);
+      }
+      // If it isn't, cache it.
+      llvm::GlobalAlias *Sel = new llvm::GlobalAlias(
+          llvm::PointerType::getUnqual(SelectorTy),
+          llvm::GlobalValue::InternalLinkage, ".objc_typed_selector_alias",
+          NULL, &TheModule);
+      TypedSelectors[Selector] = Sel;
+      return Builder.CreateLoad(Sel);
+    }
+  }
+  // Dynamically look up selectors from non-constant sources
   llvm::Value *cmd;
-  if(SelTypes == 0) {
+  if (SelTypes == 0) {
     llvm::Constant *SelFunction = TheModule.getOrInsertFunction("sel_get_uid", 
         SelectorTy, 
         PtrToInt8Ty, 
@@ -114,20 +274,60 @@
 }
 
 
-/// Generate code for a message send expression on the GNU runtime.
-// FIXME: Much of this code will need factoring out later.
-// TODO: This should take a sender argument (pointer to self in the calling
-// context)
-llvm::Value *CGObjCGNU::generateMessageSend(llvm::IRBuilder &Builder,
+llvm::Constant *CGObjCGNU::MakeConstantString(const std::string &Str, const
+    std::string &Name) {
+  llvm::Constant * ConstStr = llvm::ConstantArray::get(Str);
+  ConstStr = new llvm::GlobalVariable(ConstStr->getType(), true, 
+                               llvm::GlobalValue::InternalLinkage,
+                               ConstStr, Name, &TheModule);
+  return llvm::ConstantExpr::getGetElementPtr(ConstStr, Zeros, 2);
+}
+llvm::Constant *CGObjCGNU::MakeGlobal(const llvm::StructType *Ty,
+    std::vector<llvm::Constant*> &V, const std::string &Name) {
+  llvm::Constant *C = llvm::ConstantStruct::get(Ty, V);
+  return new llvm::GlobalVariable(Ty, false,
+      llvm::GlobalValue::InternalLinkage, C, Name, &TheModule);
+}
+llvm::Constant *CGObjCGNU::MakeGlobal(const llvm::ArrayType *Ty,
+    std::vector<llvm::Constant*> &V, const std::string &Name) {
+  llvm::Constant *C = llvm::ConstantArray::get(Ty, V);
+  return new llvm::GlobalVariable(Ty, false,
+      llvm::GlobalValue::InternalLinkage, C, Name, &TheModule);
+}
+
+/// Generate an NSConstantString object.
+//TODO: In case there are any crazy people still using the GNU runtime without
+//an OpenStep implementation, this should let them select their own class for
+//constant strings.
+llvm::Constant *CGObjCGNU::GenerateConstantString(const char *String, const
+    size_t length) {
+  std::vector<llvm::Constant*> Ivars;
+  Ivars.push_back(NULLPtr);
+  Ivars.push_back(MakeConstantString(String));
+  Ivars.push_back(llvm::ConstantInt::get(IntTy, length));
+  llvm::Constant *ObjCStr = MakeGlobal(
+    llvm::StructType::get(PtrToInt8Ty, PtrToInt8Ty, IntTy, NULL),
+    Ivars, ".objc_str");
+  ConstantStrings.push_back(
+      llvm::ConstantExpr::getBitCast(ObjCStr, PtrToInt8Ty));
+  return ObjCStr;
+}
+
+///Generates a message send where the super is the receiver.  This is a message
+///send to self with special delivery semantics indicating which class's method
+///should be called.
+llvm::Value *CGObjCGNU::GenerateMessageSendSuper(llvm::IRBuilder &Builder,
                                             const llvm::Type *ReturnTy,
                                             llvm::Value *Sender,
+                                            const char *SuperClassName,
                                             llvm::Value *Receiver,
                                             llvm::Value *Selector,
                                             llvm::Value** ArgV,
                                             unsigned ArgC) {
-  llvm::Value *cmd = getSelector(Builder, Selector, 0);
-
-  // Look up the method implementation.
+  // TODO: This should be cached, not looked up every time.
+  llvm::Value *ReceiverClass = LookupClass(Builder,
+      MakeConstantString(SuperClassName));
+  llvm::Value *cmd = GetSelector(Builder, Selector, 0);
   std::vector<const llvm::Type*> impArgTypes;
   impArgTypes.push_back(Receiver->getType());
   impArgTypes.push_back(SelectorTy);
@@ -136,6 +336,60 @@
   // return type.
   llvm::FunctionType *impType = llvm::FunctionType::get(ReturnTy, impArgTypes,
                                                         true);
+  // Construct the structure used to look up the IMP
+  llvm::StructType *ObjCSuperTy = llvm::StructType::get(Receiver->getType(),
+      IdTy, NULL);
+  llvm::Value *ObjCSuper = Builder.CreateAlloca(ObjCSuperTy);
+  Builder.CreateStore(Receiver, Builder.CreateStructGEP(ObjCSuper, 0));
+  Builder.CreateStore(ReceiverClass, Builder.CreateStructGEP(ObjCSuper, 1));
+
+  // Get the IMP
+  llvm::Constant *lookupFunction = 
+     TheModule.getOrInsertFunction("objc_msg_lookup_super",
+                                   llvm::PointerType::getUnqual(impType),
+                                   llvm::PointerType::getUnqual(ObjCSuperTy),
+                                   SelectorTy, NULL);
+  llvm::Value *lookupArgs[] = {ObjCSuper, cmd};
+  llvm::Value *imp = Builder.CreateCall(lookupFunction, lookupArgs,
+      lookupArgs+2);
+
+  // Call the method
+  llvm::SmallVector<llvm::Value*, 8> callArgs;
+  callArgs.push_back(Receiver);
+  callArgs.push_back(cmd);
+  callArgs.insert(callArgs.end(), ArgV, ArgV+ArgC);
+  return Builder.CreateCall(imp, callArgs.begin(), callArgs.end());
+}
+
+/// Generate code for a message send expression.  
+llvm::Value *CGObjCGNU::GenerateMessageSend(llvm::IRBuilder &Builder,
+                                            const llvm::Type *ReturnTy,
+                                            llvm::Value *Sender,
+                                            llvm::Value *Receiver,
+                                            llvm::Value *Selector,
+                                            llvm::Value** ArgV,
+                                            unsigned ArgC) {
+  llvm::Value *cmd = GetSelector(Builder, Selector, 0);
+
+  // Look up the method implementation.
+  std::vector<const llvm::Type*> impArgTypes;
+  const llvm::Type *RetTy;
+  //TODO: Revisit this when LLVM supports aggregate return types.
+  if (ReturnTy->isSingleValueType() && ReturnTy != llvm::Type::VoidTy) {
+    RetTy = ReturnTy;
+  } else {
+    // For struct returns allocate the space in the caller and pass it up to
+    // the sender.
+    RetTy = llvm::Type::VoidTy;
+    impArgTypes.push_back(llvm::PointerType::getUnqual(ReturnTy));
+  }
+  impArgTypes.push_back(Receiver->getType());
+  impArgTypes.push_back(SelectorTy);
+  
+  // Avoid an explicit cast on the IMP by getting a version that has the right
+  // return type.
+  llvm::FunctionType *impType = llvm::FunctionType::get(RetTy, impArgTypes,
+                                                        true);
   
   llvm::Constant *lookupFunction = 
      TheModule.getOrInsertFunction("objc_msg_lookup",
@@ -144,20 +398,489 @@
   llvm::Value *imp = Builder.CreateCall2(lookupFunction, Receiver, cmd);
 
   // Call the method.
-  llvm::SmallVector<llvm::Value*, 16> lookupArgs;
-  lookupArgs.push_back(Receiver);
-  lookupArgs.push_back(cmd);
-  lookupArgs.insert(lookupArgs.end(), ArgV, ArgV+ArgC);
-  return Builder.CreateCall(imp, lookupArgs.begin(), lookupArgs.end());
+  llvm::SmallVector<llvm::Value*, 16> Args;
+  if (!ReturnTy->isSingleValueType()) {
+    llvm::Value *Return = Builder.CreateAlloca(ReturnTy);
+    Args.push_back(Return);
+    return Return;
+  }
+  Args.push_back(Receiver);
+  Args.push_back(cmd);
+  Args.insert(Args.end(), ArgV, ArgV+ArgC);
+  return Builder.CreateCall(imp, Args.begin(), Args.end());
 }
 
+/// Generates a MethodList.  Used in construction of a objc_class and 
+/// objc_category structures.
+llvm::Constant *CGObjCGNU::GenerateMethodList(const std::string &ClassName,
+    const std::string &CategoryName, 
+    const llvm::SmallVectorImpl<llvm::Constant *> &MethodNames, 
+    const llvm::SmallVectorImpl<llvm::Constant *> &MethodTypes, 
+    bool isClassMethodList) {
+  // Get the method structure type.  
+  llvm::StructType *ObjCMethodTy = llvm::StructType::get(
+    PtrToInt8Ty, // Really a selector, but the runtime creates it us.
+    PtrToInt8Ty, // Method types
+    llvm::PointerType::getUnqual(IMPTy), //Method pointer
+    NULL);
+  std::vector<llvm::Constant*> Methods;
+  std::vector<llvm::Constant*> Elements;
+  for (unsigned int i = 0, e = MethodTypes.size(); i < e; ++i) {
+    Elements.clear();
+    Elements.push_back( llvm::ConstantExpr::getGetElementPtr(MethodNames[i],
+          Zeros, 2));
+    Elements.push_back(
+          llvm::ConstantExpr::getGetElementPtr(MethodTypes[i], Zeros, 2));
+    llvm::Constant *Method =
+      TheModule.getFunction(SymbolNameForMethod(ClassName, CategoryName,
+            MethodNames[i]->getStringValue(), isClassMethodList));
+    Method = llvm::ConstantExpr::getBitCast(Method,
+        llvm::PointerType::getUnqual(IMPTy));
+    Elements.push_back(Method);
+    Methods.push_back(llvm::ConstantStruct::get(ObjCMethodTy, Elements));
+  }
+
+  // Array of method structures
+  llvm::ArrayType *ObjCMethodArrayTy = llvm::ArrayType::get(ObjCMethodTy,
+      MethodNames.size());
+  llvm::Constant *MethodArray = llvm::ConstantArray::get(ObjCMethodArrayTy,
+      Methods);
+
+  // Structure containing list pointer, array and array count
+  llvm::SmallVector<const llvm::Type*, 16> ObjCMethodListFields;
+  llvm::PATypeHolder OpaqueNextTy = llvm::OpaqueType::get();
+  llvm::Type *NextPtrTy = llvm::PointerType::getUnqual(OpaqueNextTy);
+  llvm::StructType *ObjCMethodListTy = llvm::StructType::get(NextPtrTy, 
+      IntTy, 
+      ObjCMethodArrayTy,
+      NULL);
+  // Refine next pointer type to concrete type
+  llvm::cast<llvm::OpaqueType>(
+      OpaqueNextTy.get())->refineAbstractTypeTo(ObjCMethodListTy);
+  ObjCMethodListTy = llvm::cast<llvm::StructType>(OpaqueNextTy.get());
+
+  Methods.clear();
+  Methods.push_back(llvm::ConstantPointerNull::get(
+        llvm::PointerType::getUnqual(ObjCMethodListTy)));
+  Methods.push_back(llvm::ConstantInt::get(llvm::Type::Int32Ty,
+        MethodTypes.size()));
+  Methods.push_back(MethodArray);
+  
+  // Create an instance of the structure
+  return MakeGlobal(ObjCMethodListTy, Methods, ".objc_method_list");
+}
+
+/// Generates an IvarList.  Used in construction of a objc_class.
+llvm::Constant *CGObjCGNU::GenerateIvarList(
+    const llvm::SmallVectorImpl<llvm::Constant *>  &IvarNames,
+    const llvm::SmallVectorImpl<llvm::Constant *>  &IvarTypes,
+    const llvm::SmallVectorImpl<llvm::Constant *>  &IvarOffsets) {
+  // Get the method structure type.  
+  llvm::StructType *ObjCIvarTy = llvm::StructType::get(
+    PtrToInt8Ty,
+    PtrToInt8Ty,
+    IntTy,
+    NULL);
+  std::vector<llvm::Constant*> Ivars;
+  std::vector<llvm::Constant*> Elements;
+  for (unsigned int i = 0, e = IvarNames.size() ; i < e ; i++) {
+    Elements.clear();
+    Elements.push_back( llvm::ConstantExpr::getGetElementPtr(IvarNames[i],
+          Zeros, 2));
+    Elements.push_back( llvm::ConstantExpr::getGetElementPtr(IvarTypes[i],
+          Zeros, 2));
+    Elements.push_back(IvarOffsets[i]);
+    Ivars.push_back(llvm::ConstantStruct::get(ObjCIvarTy, Elements));
+  }
+
+  // Array of method structures
+  llvm::ArrayType *ObjCIvarArrayTy = llvm::ArrayType::get(ObjCIvarTy,
+      IvarNames.size());
+
+  
+  Elements.clear();
+  Elements.push_back(llvm::ConstantInt::get(
+        llvm::cast<llvm::IntegerType>(IntTy), (int)IvarNames.size()));
+  Elements.push_back(llvm::ConstantArray::get(ObjCIvarArrayTy, Ivars));
+  // Structure containing array and array count
+  llvm::StructType *ObjCIvarListTy = llvm::StructType::get(IntTy,
+    ObjCIvarArrayTy,
+    NULL);
+
+  // Create an instance of the structure
+  return MakeGlobal(ObjCIvarListTy, Elements, ".objc_ivar_list");
+}
+
+/// Generate a class structure
+llvm::Constant *CGObjCGNU::GenerateClassStructure(
+    llvm::Constant *MetaClass,
+    llvm::Constant *SuperClass,
+    unsigned info,
+    llvm::Constant *Name,
+    llvm::Constant *Version,
+    llvm::Constant *InstanceSize,
+    llvm::Constant *IVars,
+    llvm::Constant *Methods,
+    llvm::Constant *Protocols) {
+  // Set up the class structure
+  // Note:  Several of these are char*s when they should be ids.  This is
+  // because the runtime performs this translation on load.
+  llvm::StructType *ClassTy = llvm::StructType::get(
+      PtrToInt8Ty,        // class_pointer
+      PtrToInt8Ty,        // super_class
+      PtrToInt8Ty,        // name
+      LongTy,             // version
+      LongTy,             // info
+      LongTy,             // instance_size
+      IVars->getType(),   // ivars
+      Methods->getType(), // methods
+      // These are all filled in by the runtime, so we pretend 
+      PtrTy,              // dtable
+      PtrTy,              // subclass_list
+      PtrTy,              // sibling_class
+      PtrTy,              // protocols
+      PtrTy,              // gc_object_type
+      NULL);
+  llvm::Constant *Zero = llvm::ConstantInt::get(LongTy, 0);
+  llvm::Constant *NullP =
+    llvm::ConstantPointerNull::get(llvm::cast<llvm::PointerType>(PtrTy));
+  // Fill in the structure
+  std::vector<llvm::Constant*> Elements;
+  Elements.push_back(llvm::ConstantExpr::getBitCast(MetaClass, PtrToInt8Ty));
+  Elements.push_back(SuperClass);
+  Elements.push_back(Name);
+  Elements.push_back(Zero);
+  Elements.push_back(llvm::ConstantInt::get(LongTy, info));
+  Elements.push_back(InstanceSize);
+  Elements.push_back(IVars);
+  Elements.push_back(Methods);
+  Elements.push_back(NullP);
+  Elements.push_back(NullP);
+  Elements.push_back(NullP);
+  Elements.push_back(llvm::ConstantExpr::getBitCast(Protocols, PtrTy));
+  Elements.push_back(NullP);
+  // Create an instance of the structure
+  return MakeGlobal(ClassTy, Elements,
+      SymbolNameForClass(Name->getStringValue()));
+}
+
+llvm::Constant *CGObjCGNU::GenerateProtocolMethodList(
+    const llvm::SmallVectorImpl<llvm::Constant *>  &MethodNames,
+    const llvm::SmallVectorImpl<llvm::Constant *>  &MethodTypes) {
+  // Get the method structure type.  
+  llvm::StructType *ObjCMethodDescTy = llvm::StructType::get(
+    PtrToInt8Ty, // Really a selector, but the runtime does the casting for us.
+    PtrToInt8Ty,
+    NULL);
+  std::vector<llvm::Constant*> Methods;
+  std::vector<llvm::Constant*> Elements;
+  for (unsigned int i = 0, e = MethodTypes.size() ; i < e ; i++) {
+    Elements.clear();
+    Elements.push_back( llvm::ConstantExpr::getGetElementPtr(MethodNames[i],
+          Zeros, 2)); 
+    Elements.push_back(
+          llvm::ConstantExpr::getGetElementPtr(MethodTypes[i], Zeros, 2));
+    Methods.push_back(llvm::ConstantStruct::get(ObjCMethodDescTy, Elements));
+  }
+  llvm::ArrayType *ObjCMethodArrayTy = llvm::ArrayType::get(ObjCMethodDescTy,
+      MethodNames.size());
+  llvm::Constant *Array = llvm::ConstantArray::get(ObjCMethodArrayTy, Methods);
+  llvm::StructType *ObjCMethodDescListTy = llvm::StructType::get(
+      IntTy, ObjCMethodArrayTy, NULL);
+  Methods.clear();
+  Methods.push_back(llvm::ConstantInt::get(IntTy, MethodNames.size()));
+  Methods.push_back(Array);
+  return MakeGlobal(ObjCMethodDescListTy, Methods, ".objc_method_list");
+}
+// Create the protocol list structure used in classes, categories and so on
+llvm::Constant *CGObjCGNU::GenerateProtocolList(
+    const llvm::SmallVectorImpl<std::string> &Protocols) {
+  llvm::ArrayType *ProtocolArrayTy = llvm::ArrayType::get(PtrToInt8Ty,
+      Protocols.size());
+  llvm::StructType *ProtocolListTy = llvm::StructType::get(
+      PtrTy, //Should be a recurisve pointer, but it's always NULL here.
+      LongTy,//FIXME: Should be size_t
+      ProtocolArrayTy,
+      NULL);
+  std::vector<llvm::Constant*> Elements; 
+  for (const std::string *iter = Protocols.begin(), *endIter = Protocols.end();
+      iter != endIter ; iter++) {
+    llvm::Constant *Ptr =
+      llvm::ConstantExpr::getBitCast(ExistingProtocols[*iter], PtrToInt8Ty);
+    Elements.push_back(Ptr);
+  }
+  llvm::Constant * ProtocolArray = llvm::ConstantArray::get(ProtocolArrayTy,
+      Elements);
+  Elements.clear();
+  Elements.push_back(NULLPtr);
+  Elements.push_back(llvm::ConstantInt::get(
+        llvm::cast<llvm::IntegerType>(LongTy), Protocols.size()));
+  Elements.push_back(ProtocolArray);
+  return MakeGlobal(ProtocolListTy, Elements, ".objc_protocol_list");
+}
+
+llvm::Value *CGObjCGNU::GenerateProtocolRef(llvm::IRBuilder &Builder, const
+    char *ProtocolName) {
+  return ExistingProtocols[ProtocolName];
+}
+
+void CGObjCGNU::GenerateProtocol(const char *ProtocolName,
+    const llvm::SmallVectorImpl<std::string> &Protocols,
+    const llvm::SmallVectorImpl<llvm::Constant *>  &InstanceMethodNames,
+    const llvm::SmallVectorImpl<llvm::Constant *>  &InstanceMethodTypes,
+    const llvm::SmallVectorImpl<llvm::Constant *>  &ClassMethodNames,
+    const llvm::SmallVectorImpl<llvm::Constant *>  &ClassMethodTypes) {
+
+  llvm::Constant *ProtocolList = GenerateProtocolList(Protocols);
+  llvm::Constant *InstanceMethodList =
+    GenerateProtocolMethodList(InstanceMethodNames, InstanceMethodTypes);
+  llvm::Constant *ClassMethodList =
+    GenerateProtocolMethodList(ClassMethodNames, ClassMethodTypes);
+  // Protocols are objects containing lists of the methods implemented and
+  // protocols adopted.
+  llvm::StructType *ProtocolTy = llvm::StructType::get(IdTy,
+      PtrToInt8Ty,
+      ProtocolList->getType(),
+      InstanceMethodList->getType(),
+      ClassMethodList->getType(),
+      NULL);
+  std::vector<llvm::Constant*> Elements; 
+  // The isa pointer must be set to a magic number so the runtime knows it's
+  // the correct layout.
+  Elements.push_back(llvm::ConstantExpr::getIntToPtr(
+        llvm::ConstantInt::get(llvm::Type::Int32Ty, ProtocolVersion), IdTy));
+  Elements.push_back(MakeConstantString(ProtocolName, ".objc_protocol_name"));
+  Elements.push_back(ProtocolList);
+  Elements.push_back(InstanceMethodList);
+  Elements.push_back(ClassMethodList);
+  ExistingProtocols[ProtocolName] = 
+    llvm::ConstantExpr::getBitCast(MakeGlobal(ProtocolTy, Elements,
+          ".objc_protocol"), IdTy);
+}
+
+void CGObjCGNU::GenerateCategory(
+           const char *ClassName,
+           const char *CategoryName,
+           const llvm::SmallVectorImpl<llvm::Constant *>  &InstanceMethodNames,
+           const llvm::SmallVectorImpl<llvm::Constant *>  &InstanceMethodTypes,
+           const llvm::SmallVectorImpl<llvm::Constant *>  &ClassMethodNames,
+           const llvm::SmallVectorImpl<llvm::Constant *>  &ClassMethodTypes,
+           const llvm::SmallVectorImpl<std::string> &Protocols) {
+  std::vector<llvm::Constant*> Elements;
+  Elements.push_back(MakeConstantString(CategoryName));
+  Elements.push_back(MakeConstantString(ClassName));
+  // Instance method list 
+  Elements.push_back(llvm::ConstantExpr::getBitCast(GenerateMethodList(
+          ClassName, CategoryName, InstanceMethodNames, InstanceMethodTypes,
+          false), PtrTy));
+  // Class method list
+  Elements.push_back(llvm::ConstantExpr::getBitCast(GenerateMethodList(
+          ClassName, CategoryName, ClassMethodNames, ClassMethodTypes, true),
+        PtrTy));
+  // Protocol list
+  Elements.push_back(llvm::ConstantExpr::getBitCast(
+        GenerateProtocolList(Protocols), PtrTy));
+  Categories.push_back(llvm::ConstantExpr::getBitCast(
+        MakeGlobal(llvm::StructType::get(PtrToInt8Ty, PtrToInt8Ty, PtrTy,
+            PtrTy, PtrTy, NULL), Elements), PtrTy));
+}
+void CGObjCGNU::GenerateClass(
+           const char *ClassName,
+           const char *SuperClassName,
+           const int instanceSize,
+           const llvm::SmallVectorImpl<llvm::Constant *>  &IvarNames,
+           const llvm::SmallVectorImpl<llvm::Constant *>  &IvarTypes,
+           const llvm::SmallVectorImpl<llvm::Constant *>  &IvarOffsets,
+           const llvm::SmallVectorImpl<llvm::Constant *>  &InstanceMethodNames,
+           const llvm::SmallVectorImpl<llvm::Constant *>  &InstanceMethodTypes,
+           const llvm::SmallVectorImpl<llvm::Constant *>  &ClassMethodNames,
+           const llvm::SmallVectorImpl<llvm::Constant *>  &ClassMethodTypes,
+           const llvm::SmallVectorImpl<std::string> &Protocols) {
+  // Get the superclass pointer.
+  llvm::Constant *SuperClass;
+  if (SuperClassName) {
+    SuperClass = MakeConstantString(SuperClassName, ".super_class_name");
+  } else {
+    SuperClass = llvm::ConstantPointerNull::get(
+        llvm::cast<llvm::PointerType>(PtrToInt8Ty));
+  }
+  llvm::Constant * Name = MakeConstantString(ClassName, ".class_name");
+  // Empty vector used to construct empty method lists
+  llvm::SmallVector<llvm::Constant*, 1>  empty;
+  // Generate the method and instance variable lists
+  llvm::Constant *MethodList = GenerateMethodList(ClassName, "",
+      InstanceMethodNames, InstanceMethodTypes, false);
+  llvm::Constant *ClassMethodList = GenerateMethodList(ClassName, "",
+      ClassMethodNames, ClassMethodTypes, true);
+  llvm::Constant *IvarList = GenerateIvarList(IvarNames, IvarTypes,
+      IvarOffsets);
+  //Generate metaclass for class methods
+  llvm::Constant *MetaClassStruct = GenerateClassStructure(NULLPtr,
+      NULLPtr, 0x2L, NULLPtr, 0, Zeros[0], GenerateIvarList(
+        empty, empty, empty), ClassMethodList, NULLPtr);
+  // Generate the class structure
+  llvm::Constant *ClassStruct = GenerateClassStructure(MetaClassStruct,
+      SuperClass, 0x1L, Name, 0,
+      llvm::ConstantInt::get(llvm::Type::Int32Ty, instanceSize), IvarList,
+      MethodList, GenerateProtocolList(Protocols));
+  // Add class structure to list to be added to the symtab later
+  ClassStruct = llvm::ConstantExpr::getBitCast(ClassStruct, PtrToInt8Ty);
+  Classes.push_back(ClassStruct);
+}
+
+llvm::Function *CGObjCGNU::ModuleInitFunction() { 
+  // Only emit an ObjC load function if no Objective-C stuff has been called
+  if (Classes.empty() && Categories.empty() && ConstantStrings.empty() &&
+      ExistingProtocols.empty() && TypedSelectors.empty() &&
+      UntypedSelectors.empty() == 0)
+    return NULL;
+  
+  std::vector<llvm::Constant*> Elements;
+  // Generate statics list:
+  llvm::ArrayType *StaticsArrayTy = llvm::ArrayType::get(PtrToInt8Ty,
+      ConstantStrings.size() + 1);
+  ConstantStrings.push_back(NULLPtr);
+  Elements.push_back(MakeConstantString("NSConstantString",
+        ".objc_static_class_name"));
+  Elements.push_back(llvm::ConstantArray::get(StaticsArrayTy, ConstantStrings));
+  llvm::StructType *StaticsListTy = 
+    llvm::StructType::get(PtrToInt8Ty, StaticsArrayTy, NULL);
+  llvm::Constant *Statics = 
+    MakeGlobal(StaticsListTy, Elements, ".objc_statics");
+  Statics = new
+    llvm::GlobalVariable(llvm::PointerType::getUnqual(StaticsListTy), false,
+        llvm::GlobalValue::InternalLinkage, Statics, ".objc_statics_ptr",
+        &TheModule);
+  Statics = llvm::ConstantExpr::getBitCast(Statics, PtrTy);
+  // Array of classes, categories, and constant objects
+  llvm::ArrayType *ClassListTy = llvm::ArrayType::get(PtrToInt8Ty,
+      Classes.size() + Categories.size()  + 2);
+  llvm::StructType *SymTabTy = llvm::StructType::get(
+      LongTy,
+      SelectorTy,
+      llvm::Type::Int16Ty,
+      llvm::Type::Int16Ty,
+      ClassListTy,
+      NULL);
+
+  Elements.clear();
+  // Pointer to an array of selectors used in this module.
+  std::vector<llvm::Constant*> Selectors;
+  for (std::map<TypedSelector, llvm::GlobalAlias*>::iterator
+     iter = TypedSelectors.begin(), iterEnd = TypedSelectors.end();
+     iter != iterEnd ; ++iter) {
+    Elements.push_back(MakeConstantString((*iter).first.first,
+          ".objc_sel_name"));
+    Elements.push_back(MakeConstantString((*iter).first.second,
+          ".objc_sel_types"));
+    Selectors.push_back(llvm::ConstantStruct::get(SelStructTy, Elements));
+    Elements.clear();
+  }
+  for (llvm::StringMap<llvm::GlobalAlias*>::iterator
+      iter = UntypedSelectors.begin(), iterEnd = UntypedSelectors.end();
+      iter != iterEnd; iter++) {
+    Elements.push_back(
+        MakeConstantString((*iter).getKeyData(), ".objc_sel_name"));
+    Elements.push_back(NULLPtr);
+    Selectors.push_back(llvm::ConstantStruct::get(SelStructTy, Elements));
+    Elements.clear();
+  }
+  Elements.push_back(NULLPtr);
+  Elements.push_back(NULLPtr);
+  Selectors.push_back(llvm::ConstantStruct::get(SelStructTy, Elements));
+  Elements.clear();
+  // Number of static selectors
+  Elements.push_back(llvm::ConstantInt::get(LongTy, Selectors.size() ));
+  llvm::Constant *SelectorList = MakeGlobal(
+          llvm::ArrayType::get(SelStructTy, Selectors.size()), Selectors,
+          ".objc_selector_list");
+  Elements.push_back(llvm::ConstantExpr::getBitCast(SelectorList, SelectorTy));
+
+  // Now that all of the static selectors exist, create pointers to them.
+  int index = 0;
+  for (std::map<TypedSelector, llvm::GlobalAlias*>::iterator
+     iter=TypedSelectors.begin(), iterEnd =TypedSelectors.end();
+     iter != iterEnd; ++iter) {
+    llvm::Constant *Idxs[] = {Zeros[0],
+      llvm::ConstantInt::get(llvm::Type::Int32Ty, index++), Zeros[0]};
+    llvm::GlobalVariable *SelPtr = new llvm::GlobalVariable(SelectorTy, true,
+        llvm::GlobalValue::InternalLinkage,
+        llvm::ConstantExpr::getGetElementPtr(SelectorList, Idxs, 2),
+        ".objc_sel_ptr", &TheModule);
+    (*iter).second->setAliasee(SelPtr);
+  }
+  for (llvm::StringMap<llvm::GlobalAlias*>::iterator
+      iter=UntypedSelectors.begin(), iterEnd = UntypedSelectors.end();
+      iter != iterEnd; iter++) {
+    llvm::Constant *Idxs[] = {Zeros[0],
+      llvm::ConstantInt::get(llvm::Type::Int32Ty, index++), Zeros[0]};
+    llvm::GlobalVariable *SelPtr = new llvm::GlobalVariable(SelectorTy, true,
+        llvm::GlobalValue::InternalLinkage,
+        llvm::ConstantExpr::getGetElementPtr(SelectorList, Idxs, 2),
+        ".objc_sel_ptr", &TheModule);
+    (*iter).second->setAliasee(SelPtr);
+  }
+  // Number of classes defined.
+  Elements.push_back(llvm::ConstantInt::get(llvm::Type::Int16Ty, 
+        Classes.size()));
+  // Number of categories defined
+  Elements.push_back(llvm::ConstantInt::get(llvm::Type::Int16Ty, 
+        Categories.size()));
+  // Create an array of classes, then categories, then static object instances
+  Classes.insert(Classes.end(), Categories.begin(), Categories.end());
+  //  NULL-terminated list of static object instances (mainly constant strings)
+  Classes.push_back(Statics);
+  Classes.push_back(NULLPtr);
+  llvm::Constant *ClassList = llvm::ConstantArray::get(ClassListTy, Classes);
+  Elements.push_back(ClassList);
+  // Construct the symbol table 
+  llvm::Constant *SymTab= MakeGlobal(SymTabTy, Elements);
+
+  // The symbol table is contained in a module which has some version-checking
+  // constants
+  llvm::StructType * ModuleTy = llvm::StructType::get(LongTy, LongTy,
+      PtrToInt8Ty, llvm::PointerType::getUnqual(SymTabTy), NULL);
+  Elements.clear();
+  // Runtime version used for compatibility checking.
+  Elements.push_back(llvm::ConstantInt::get(LongTy, RuntimeVersion));
+  //FIXME: Should be sizeof(ModuleTy)
+  Elements.push_back(llvm::ConstantInt::get(LongTy, 16));
+  //FIXME: Should be the path to the file where this module was declared
+  Elements.push_back(NULLPtr);
+  Elements.push_back(SymTab);
+  llvm::Value *Module = MakeGlobal(ModuleTy, Elements);
+
+  // Create the load function calling the runtime entry point with the module
+  // structure
+  std::vector<const llvm::Type*> VoidArgs;
+  llvm::Function * LoadFunction = llvm::Function::Create(
+      llvm::FunctionType::get(llvm::Type::VoidTy, VoidArgs, false),
+      llvm::GlobalValue::InternalLinkage, ".objc_load_function",
+      &TheModule);
+  llvm::BasicBlock *EntryBB = llvm::BasicBlock::Create("entry", LoadFunction);
+  llvm::IRBuilder Builder;
+  Builder.SetInsertPoint(EntryBB);
+  llvm::Value *Register = TheModule.getOrInsertFunction("__objc_exec_class",
+      llvm::Type::VoidTy, llvm::PointerType::getUnqual(ModuleTy), NULL);
+  Builder.CreateCall(Register, Module);
+  Builder.CreateRetVoid();
+  return LoadFunction;
+}
 llvm::Function *CGObjCGNU::MethodPreamble(
+                                         const std::string &ClassName,
+                                         const std::string &CategoryName,
+                                         const std::string &MethodName,
                                          const llvm::Type *ReturnTy,
                                          const llvm::Type *SelfTy,
                                          const llvm::Type **ArgTy,
                                          unsigned ArgC,
+                                         bool isClassMethod,
                                          bool isVarArg) {
   std::vector<const llvm::Type*> Args;
+  if (!ReturnTy->isFirstClassType() && ReturnTy != llvm::Type::VoidTy) {
+    Args.push_back(llvm::PointerType::getUnqual(ReturnTy));
+    ReturnTy = llvm::Type::VoidTy;
+  }
   Args.push_back(SelfTy);
   Args.push_back(SelectorTy);
   Args.insert(Args.end(), ArgTy, ArgTy+ArgC);
@@ -165,12 +888,20 @@
   llvm::FunctionType *MethodTy = llvm::FunctionType::get(ReturnTy,
       Args,
       isVarArg);
+  std::string FunctionName = SymbolNameForMethod(ClassName, CategoryName,
+      MethodName, isClassMethod);
+
   llvm::Function *Method = llvm::Function::Create(MethodTy,
       llvm::GlobalValue::InternalLinkage,
-      ".objc.method",
+      FunctionName,
       &TheModule);
-  // Set the names of the hidden arguments
   llvm::Function::arg_iterator AI = Method->arg_begin();
+  // Name the struct return argument.
+  // FIXME: This is probably the wrong test.
+  if (!ReturnTy->isFirstClassType() && ReturnTy != llvm::Type::VoidTy) {
+    AI->setName("agg.result");
+    ++AI;
+  }
   AI->setName("self");
   ++AI;
   AI->setName("_cmd");
diff --git a/lib/CodeGen/CGObjCRuntime.h b/lib/CodeGen/CGObjCRuntime.h
index 9ee067b..6ec6e0c 100644
--- a/lib/CodeGen/CGObjCRuntime.h
+++ b/lib/CodeGen/CGObjCRuntime.h
@@ -15,6 +15,7 @@
 
 #ifndef CLANG_CODEGEN_OBCJRUNTIME_H
 #define CLANG_CODEGEN_OBCJRUNTIME_H
+#include "llvm/ADT/SmallVector.h"
 
 namespace llvm {
   class IRBuilder;
@@ -25,32 +26,89 @@
   class Function;
 }
 
-
 namespace clang {
 namespace CodeGen {
 
-// Implements runtime-specific code generation functions
+//FIXME Several methods should be pure virtual but aren't to avoid the
+//partially-implemented subclass breaking.
+
+/// Implements runtime-specific code generation functions.
 class CGObjCRuntime {
 public:
   virtual ~CGObjCRuntime();
   
   /// Generate an Objective-C message send operation
-  virtual llvm::Value *generateMessageSend(llvm::IRBuilder &Builder,
+  virtual llvm::Value *GenerateMessageSend(llvm::IRBuilder &Builder,
                                            const llvm::Type *ReturnTy,
                                            llvm::Value *Sender,
                                            llvm::Value *Receiver,
                                            llvm::Value *Selector,
                                            llvm::Value** ArgV,
-                                           unsigned ArgC) = 0;
+                                           unsigned ArgC) =0;
   /// Generate the function required to register all Objective-C components in
   /// this compilation unit with the runtime library.
-  virtual llvm::Function *ModuleInitFunction() { return 0; }
+  virtual llvm::Function *ModuleInitFunction() =0;
+  /// Get a selector for the specified name and type values
+  virtual llvm::Value *GetSelector(llvm::IRBuilder &Builder,
+      llvm::Value *SelName,
+      llvm::Value *SelTypes) =0;
+  /// Generate a constant string object
+  virtual llvm::Constant *GenerateConstantString(const char *String, const size_t
+      length) =0;
+  /// Generate a category.  A category contains a list of methods (and
+  /// accompanying metadata) and a list of protocols.
+  virtual void GenerateCategory(const char *ClassName, const char *CategoryName,
+             const llvm::SmallVectorImpl<llvm::Constant *>  &InstanceMethodNames,
+             const llvm::SmallVectorImpl<llvm::Constant *>  &InstanceMethodTypes,
+             const llvm::SmallVectorImpl<llvm::Constant *>  &ClassMethodNames,
+             const llvm::SmallVectorImpl<llvm::Constant *>  &ClassMethodTypes,
+             const llvm::SmallVectorImpl<std::string> &Protocols) =0;
+  /// Generate a class stucture for this class.
+  virtual void GenerateClass(
+             const char *ClassName,
+             const char *SuperClassName,
+             const int instanceSize,
+             const llvm::SmallVectorImpl<llvm::Constant *>  &IvarNames,
+             const llvm::SmallVectorImpl<llvm::Constant *>  &IvarTypes,
+             const llvm::SmallVectorImpl<llvm::Constant *>  &IvarOffsets,
+             const llvm::SmallVectorImpl<llvm::Constant *>  &InstanceMethodNames,
+             const llvm::SmallVectorImpl<llvm::Constant *>  &InstanceMethodTypes,
+             const llvm::SmallVectorImpl<llvm::Constant *>  &ClassMethodNames,
+             const llvm::SmallVectorImpl<llvm::Constant *>  &ClassMethodTypes,
+             const llvm::SmallVectorImpl<std::string> &Protocols) =0;
+  /// Generate a reference to the named protocol.
+  virtual llvm::Value *GenerateProtocolRef(llvm::IRBuilder &Builder, const char
+      *ProtocolName) =0;
+  virtual llvm::Value *GenerateMessageSendSuper(llvm::IRBuilder &Builder,
+                                            const llvm::Type *ReturnTy,
+                                            llvm::Value *Sender,
+                                            const char *SuperClassName,
+                                            llvm::Value *Receiver,
+                                            llvm::Value *Selector,
+                                            llvm::Value** ArgV,
+                                            unsigned ArgC) {return NULL;};
+  /// Generate the named protocol.  Protocols contain method metadata but no 
+  /// implementations. 
+  virtual void GenerateProtocol(const char *ProtocolName,
+    const llvm::SmallVectorImpl<std::string> &Protocols,
+    const llvm::SmallVectorImpl<llvm::Constant *>  &InstanceMethodNames,
+    const llvm::SmallVectorImpl<llvm::Constant *>  &InstanceMethodTypes,
+    const llvm::SmallVectorImpl<llvm::Constant *>  &ClassMethodNames,
+    const llvm::SmallVectorImpl<llvm::Constant *>  &ClassMethodTypes) =0;
   /// Generate a function preamble for a method with the specified types
-  virtual llvm::Function *MethodPreamble(const llvm::Type *ReturnTy,
+  virtual llvm::Function *MethodPreamble(
+                                         const std::string &ClassName,
+                                         const std::string &CategoryName,
+                                         const std::string &MethodName,
+                                         const llvm::Type *ReturnTy,
                                          const llvm::Type *SelfTy,
                                          const llvm::Type **ArgTy,
                                          unsigned ArgC,
+                                         bool isClassMethod,
                                          bool isVarArg) = 0;
+  /// Look up the class for the specified name
+  virtual llvm::Value *LookupClass(llvm::IRBuilder &Builder, llvm::Value
+      *ClassName) =0;
   /// If instance variable addresses are determined at runtime then this should
   /// return true, otherwise instance variables will be accessed directly from
   /// the structure.  If this returns true then @defs is invalid for this
diff --git a/lib/CodeGen/CodeGenFunction.cpp b/lib/CodeGen/CodeGenFunction.cpp
index 0a016c6..26a0cfb 100644
--- a/lib/CodeGen/CodeGenFunction.cpp
+++ b/lib/CodeGen/CodeGenFunction.cpp
@@ -65,11 +65,22 @@
   for (unsigned i=0 ; i<OMD->param_size() ; i++) {
     ParamTypes.push_back(ConvertType(OMD->getParamDecl(i)->getType()));
   }
-  CurFn =CGM.getObjCRuntime()->MethodPreamble(ConvertType(OMD->getResultType()),
-                      llvm::PointerType::getUnqual(llvm::Type::Int32Ty),
-                                              ParamTypes.begin(),
-                                              OMD->param_size(),
-                                              OMD->isVariadic());
+  std::string CategoryName = "";
+  if (ObjCCategoryImplDecl *OCD =
+    dyn_cast<ObjCCategoryImplDecl>(OMD->getMethodContext())) {
+    CategoryName = OCD->getName();
+  }
+
+  CurFn =CGM.getObjCRuntime()->MethodPreamble(
+                            OMD->getClassInterface()->getName(),
+                            CategoryName,
+                            OMD->getSelector().getName(),
+                            ConvertType(OMD->getResultType()),
+                            llvm::PointerType::getUnqual(llvm::Type::Int32Ty),
+                            ParamTypes.begin(),
+                            OMD->param_size(),
+                            !OMD->isInstance(),
+                            OMD->isVariadic());
   llvm::BasicBlock *EntryBB = llvm::BasicBlock::Create("entry", CurFn);
   
   // Create a marker to make it easy to insert allocas into the entryblock
diff --git a/lib/CodeGen/CodeGenModule.cpp b/lib/CodeGen/CodeGenModule.cpp
index 633aa20..6b9e69e 100644
--- a/lib/CodeGen/CodeGenModule.cpp
+++ b/lib/CodeGen/CodeGenModule.cpp
@@ -25,6 +25,7 @@
 #include "llvm/DerivedTypes.h"
 #include "llvm/Module.h"
 #include "llvm/Intrinsics.h"
+#include "llvm/Target/TargetData.h"
 #include "llvm/Analysis/Verifier.h"
 #include <algorithm>
 using namespace clang;
@@ -50,10 +51,10 @@
 }
 
 CodeGenModule::~CodeGenModule() {
+  EmitStatics();
   llvm::Function *ObjCInitFunction = Runtime->ModuleInitFunction();
   if (ObjCInitFunction)
     AddGlobalCtor(ObjCInitFunction);
-  EmitStatics();
   EmitGlobalCtors();
   EmitAnnotations();
   delete Runtime;
@@ -279,6 +280,154 @@
   if (OMD->getBody())
     CodeGenFunction(*this).GenerateObjCMethod(OMD);
 }
+void CodeGenModule::EmitObjCProtocolImplementation(const ObjCProtocolDecl *PD){
+  llvm::SmallVector<std::string, 16> Protocols;
+  for (unsigned i = 0, e = PD->getNumReferencedProtocols() ; i < e ; i++)
+    Protocols.push_back(PD->getReferencedProtocols()[i]->getName());
+  llvm::SmallVector<llvm::Constant*, 16> InstanceMethodNames;
+  llvm::SmallVector<llvm::Constant*, 16> InstanceMethodTypes;
+  for (ObjCProtocolDecl::instmeth_iterator iter = PD->instmeth_begin(),
+      endIter = PD->instmeth_end() ; iter != endIter ; iter++) {
+    std::string TypeStr;
+    Context.getObjCEncodingForMethodDecl((*iter),TypeStr);
+    InstanceMethodNames.push_back(
+        GetAddrOfConstantString((*iter)->getSelector().getName()));
+    InstanceMethodTypes.push_back(GetAddrOfConstantString(TypeStr));
+  }
+  // Collect information about class methods:
+  llvm::SmallVector<llvm::Constant*, 16> ClassMethodNames;
+  llvm::SmallVector<llvm::Constant*, 16> ClassMethodTypes;
+  for (ObjCProtocolDecl::classmeth_iterator iter = PD->classmeth_begin(),
+      endIter = PD->classmeth_end() ; iter != endIter ; iter++) {
+    std::string TypeStr;
+    Context.getObjCEncodingForMethodDecl((*iter),TypeStr);
+    ClassMethodNames.push_back(
+        GetAddrOfConstantString((*iter)->getSelector().getName()));
+    ClassMethodTypes.push_back(GetAddrOfConstantString(TypeStr));
+  }
+  Runtime->GenerateProtocol(PD->getName(), Protocols, InstanceMethodNames,
+      InstanceMethodTypes, ClassMethodNames, ClassMethodTypes);
+}
+
+void CodeGenModule::EmitObjCCategoryImpl(const ObjCCategoryImplDecl *OCD) {
+
+  // Collect information about instance methods
+  llvm::SmallVector<llvm::Constant*, 16> InstanceMethodNames;
+  llvm::SmallVector<llvm::Constant*, 16> InstanceMethodTypes;
+  for (ObjCCategoryDecl::instmeth_iterator iter = OCD->instmeth_begin(),
+      endIter = OCD->instmeth_end() ; iter != endIter ; iter++) {
+    std::string TypeStr;
+    Context.getObjCEncodingForMethodDecl((*iter),TypeStr);
+    InstanceMethodNames.push_back(
+        GetAddrOfConstantString((*iter)->getSelector().getName()));
+    InstanceMethodTypes.push_back(GetAddrOfConstantString(TypeStr));
+  }
+
+  // Collect information about class methods
+  llvm::SmallVector<llvm::Constant*, 16> ClassMethodNames;
+  llvm::SmallVector<llvm::Constant*, 16> ClassMethodTypes;
+  for (ObjCCategoryDecl::classmeth_iterator iter = OCD->classmeth_begin(),
+      endIter = OCD->classmeth_end() ; iter != endIter ; iter++) {
+    std::string TypeStr;
+    Context.getObjCEncodingForMethodDecl((*iter),TypeStr);
+    ClassMethodNames.push_back(
+        GetAddrOfConstantString((*iter)->getSelector().getName()));
+    ClassMethodTypes.push_back(GetAddrOfConstantString(TypeStr));
+  }
+
+  // Collect the names of referenced protocols
+  llvm::SmallVector<std::string, 16> Protocols;
+  ObjCInterfaceDecl * ClassDecl = (ObjCInterfaceDecl*)OCD->getClassInterface();
+  for (unsigned i=0 ; i<ClassDecl->getNumIntfRefProtocols() ; i++)
+    Protocols.push_back(ClassDecl->getReferencedProtocols()[i]->getName());
+
+  // Generate the category
+  Runtime->GenerateCategory(OCD->getClassInterface()->getName(),
+      OCD->getName(), InstanceMethodNames, InstanceMethodTypes,
+      ClassMethodNames, ClassMethodTypes, Protocols);
+}
+
+void CodeGenModule::EmitObjCClassImplementation(
+    const ObjCImplementationDecl *OID) {
+  // Get the superclass name.
+  const ObjCInterfaceDecl * SCDecl = OID->getClassInterface()->getSuperClass();
+  const char * SCName = NULL;
+  if (SCDecl) {
+    SCName = SCDecl->getName();
+  }
+
+  // Get the class name
+  ObjCInterfaceDecl * ClassDecl = (ObjCInterfaceDecl*)OID->getClassInterface();
+  const char * ClassName = ClassDecl->getName();
+
+  // Get the size of instances.  For runtimes that support late-bound instances
+  // this should probably be something different (size just of instance
+  // varaibles in this class, not superclasses?).
+  int instanceSize = 0;
+  const llvm::Type *ObjTy;
+  if (!Runtime->LateBoundIVars()) {
+    ObjTy = getTypes().ConvertType(Context.getObjCInterfaceType(ClassDecl));
+    instanceSize = TheTargetData.getABITypeSize(ObjTy);
+  }
+
+  // Collect information about instance variables.
+  llvm::SmallVector<llvm::Constant*, 16> IvarNames;
+  llvm::SmallVector<llvm::Constant*, 16> IvarTypes;
+  llvm::SmallVector<llvm::Constant*, 16> IvarOffsets;
+  const llvm::StructLayout *Layout =
+    TheTargetData.getStructLayout(cast<llvm::StructType>(ObjTy));
+  ObjTy = llvm::PointerType::getUnqual(ObjTy);
+  for (ObjCInterfaceDecl::ivar_iterator iter = ClassDecl->ivar_begin(),
+      endIter = ClassDecl->ivar_end() ; iter != endIter ; iter++) {
+      // Store the name
+      IvarNames.push_back(GetAddrOfConstantString((*iter)->getName()));
+      // Get the type encoding for this ivar
+      std::string TypeStr;
+      llvm::SmallVector<const RecordType *, 8> EncodingRecordTypes;
+      Context.getObjCEncodingForType((*iter)->getType(), TypeStr,
+                                     EncodingRecordTypes);
+      IvarTypes.push_back(GetAddrOfConstantString(TypeStr));
+      // Get the offset
+      int offset =
+        (int)Layout->getElementOffset(getTypes().getLLVMFieldNo(*iter));
+      IvarOffsets.push_back(
+          llvm::ConstantInt::get(llvm::Type::Int32Ty, offset));
+  }
+
+  // Collect information about instance methods
+  llvm::SmallVector<llvm::Constant*, 16> InstanceMethodNames;
+  llvm::SmallVector<llvm::Constant*, 16> InstanceMethodTypes;
+  for (ObjCImplementationDecl::instmeth_iterator iter = OID->instmeth_begin(),
+      endIter = OID->instmeth_end() ; iter != endIter ; iter++) {
+    std::string TypeStr;
+    Context.getObjCEncodingForMethodDecl((*iter),TypeStr);
+    InstanceMethodNames.push_back(
+        GetAddrOfConstantString((*iter)->getSelector().getName()));
+    InstanceMethodTypes.push_back(GetAddrOfConstantString(TypeStr));
+  }
+
+  // Collect information about class methods
+  llvm::SmallVector<llvm::Constant*, 16> ClassMethodNames;
+  llvm::SmallVector<llvm::Constant*, 16> ClassMethodTypes;
+  for (ObjCImplementationDecl::classmeth_iterator iter = OID->classmeth_begin(),
+      endIter = OID->classmeth_end() ; iter != endIter ; iter++) {
+    std::string TypeStr;
+    Context.getObjCEncodingForMethodDecl((*iter),TypeStr);
+    ClassMethodNames.push_back(
+        GetAddrOfConstantString((*iter)->getSelector().getName()));
+    ClassMethodTypes.push_back(GetAddrOfConstantString(TypeStr));
+  }
+  // Collect the names of referenced protocols
+  llvm::SmallVector<std::string, 16> Protocols;
+  for (unsigned i = 0, e = ClassDecl->getNumIntfRefProtocols() ; i < e ; i++)
+    Protocols.push_back(ClassDecl->getReferencedProtocols()[i]->getName());
+
+  // Generate the category
+  Runtime->GenerateClass(ClassName, SCName, instanceSize, IvarNames, IvarTypes,
+      IvarOffsets, InstanceMethodNames, InstanceMethodTypes, ClassMethodNames,
+      ClassMethodTypes, Protocols);
+}
+
 
 void CodeGenModule::EmitFunction(const FunctionDecl *FD) {
   // If this is not a prototype, emit the body.
@@ -623,6 +772,7 @@
   return MemSetFn = getIntrinsic(IID);
 }
 
+// FIXME: This needs moving into an Apple Objective-C runtime class
 llvm::Constant *CodeGenModule::
 GetAddrOfConstantCFString(const std::string &str) {
   llvm::StringMapEntry<llvm::Constant *> &Entry = 
diff --git a/lib/CodeGen/CodeGenModule.h b/lib/CodeGen/CodeGenModule.h
index 992a3bf..3e77526 100644
--- a/lib/CodeGen/CodeGenModule.h
+++ b/lib/CodeGen/CodeGenModule.h
@@ -32,6 +32,9 @@
   class ASTContext;
   class FunctionDecl;
   class ObjCMethodDecl;
+  class ObjCImplementationDecl;
+  class ObjCCategoryImplDecl;
+  class ObjCProtocolDecl;
   class Decl;
   class Expr;
   class Stmt;
@@ -114,6 +117,9 @@
   void EmitStatics(void);
 
   void EmitObjCMethod(const ObjCMethodDecl *OMD);
+  void EmitObjCCategoryImpl(const ObjCCategoryImplDecl *OCD);
+  void EmitObjCClassImplementation(const ObjCImplementationDecl *OID);
+  void EmitObjCProtocolImplementation(const ObjCProtocolDecl *PD);
   void EmitFunction(const FunctionDecl *FD);
   void EmitGlobalVar(const VarDecl *D);
   void EmitGlobalVarInit(const VarDecl *D);
diff --git a/lib/CodeGen/ModuleBuilder.cpp b/lib/CodeGen/ModuleBuilder.cpp
index 1184307..b37b8d3 100644
--- a/lib/CodeGen/ModuleBuilder.cpp
+++ b/lib/CodeGen/ModuleBuilder.cpp
@@ -67,6 +67,24 @@
       
       if (FunctionDecl *FD = dyn_cast<FunctionDecl>(D)) {
         Builder->EmitFunction(FD);
+      } else if (isa<ObjCClassDecl>(D)){
+        //Forward declaration.  Only used for type checking.
+      } else if (ObjCProtocolDecl *PD = dyn_cast<ObjCProtocolDecl>(D)){
+        // Generate Protocol object.
+        Builder->EmitObjCProtocolImplementation(PD);
+      } else if (isa<ObjCCategoryDecl>(D)){
+        //Only used for typechecking.
+      } else if (ObjCCategoryImplDecl *OCD = dyn_cast<ObjCCategoryImplDecl>(D)){
+        // Generate methods, attach to category structure
+        Builder->EmitObjCCategoryImpl(OCD);
+      } else if (ObjCImplementationDecl * OID = 
+          dyn_cast<ObjCImplementationDecl>(D)){
+        // Generate methods, attach to class structure
+        Builder->EmitObjCClassImplementation(OID);
+      } else if (isa<ObjCInterfaceDecl>(D)){
+        // Ignore - generated when the implementation decl is CodeGen'd
+      } else if (ObjCMethodDecl *OMD = dyn_cast<ObjCMethodDecl>(D)){
+        Builder->EmitObjCMethod(OMD);
       } else if (VarDecl *VD = dyn_cast<VarDecl>(D)) {
         if (VD->isFileVarDecl())
           Builder->EmitGlobalVarDeclarator(VD);
