Index: tools/obj2yaml/CMakeLists.txt =================================================================== --- tools/obj2yaml/CMakeLists.txt +++ tools/obj2yaml/CMakeLists.txt @@ -4,5 +4,5 @@ ) add_llvm_utility(obj2yaml - obj2yaml.cpp coff2yaml.cpp + obj2yaml.cpp coff2yaml.cpp Error.cpp ) Index: tools/obj2yaml/Error.h =================================================================== --- /dev/null +++ tools/obj2yaml/Error.h @@ -0,0 +1,42 @@ +//===- Error.h - system_error extensions for obj2yaml -----------*- C++ -*-===// +// +// The LLVM Compiler Infrastructure +// +// This file is distributed under the University of Illinois Open Source +// License. See LICENSE.TXT for details. +// +//===----------------------------------------------------------------------===// + +#ifndef LLVM_TOOLS_ERROR_H +#define LLVM_TOOLS_ERROR_H + +#include "llvm/Support/system_error.h" + +namespace llvm { + +const error_category &obj2yaml_category(); + +struct obj2yaml_error { + enum _ { + success = 0, + file_not_found, + unrecognized_file_format, + unsupported_obj_file_format + }; + _ v_; + + obj2yaml_error(_ v) : v_(v) {} + explicit obj2yaml_error(int v) : v_(_(v)) {} + operator int() const {return v_;} +}; + +inline error_code make_error_code(obj2yaml_error e) { + return error_code(static_cast(e), obj2yaml_category()); +} + +template <> struct is_error_code_enum : std::true_type { }; +template <> struct is_error_code_enum : std::true_type { }; + +} // namespace llvm + +#endif Index: tools/obj2yaml/Error.cpp =================================================================== --- /dev/null +++ tools/obj2yaml/Error.cpp @@ -0,0 +1,54 @@ +//===- Error.cpp - system_error extensions for obj2yaml ---------*- C++ -*-===// +// +// The LLVM Compiler Infrastructure +// +// This file is distributed under the University of Illinois Open Source +// License. See LICENSE.TXT for details. +// +//===----------------------------------------------------------------------===// + +#include "Error.h" +#include "llvm/Support/ErrorHandling.h" + +using namespace llvm; + +namespace { +class _obj2yaml_error_category : public error_category { +public: + const char *name() const override; + std::string message(int ev) const override; + error_condition default_error_condition(int ev) const override; +}; +} // namespace + +const char *_obj2yaml_error_category::name() const { return "obj2yaml"; } + +std::string _obj2yaml_error_category::message(int ev) const { + switch (ev) { + case obj2yaml_error::success: + return "Success"; + case obj2yaml_error::file_not_found: + return "No such file."; + case obj2yaml_error::unrecognized_file_format: + return "Unrecognized file type."; + case obj2yaml_error::unsupported_obj_file_format: + return "Unsupported object file format."; + default: + llvm_unreachable("An enumerator of obj2yaml_error does not have a message " + "defined."); + } +} + +error_condition +_obj2yaml_error_category::default_error_condition(int ev) const { + if (ev == obj2yaml_error::success) + return errc::success; + return errc::invalid_argument; +} + +namespace llvm { +const error_category &obj2yaml_category() { + static _obj2yaml_error_category o; + return o; +} +} // namespace llvm Index: tools/obj2yaml/coff2yaml.cpp =================================================================== --- tools/obj2yaml/coff2yaml.cpp +++ tools/obj2yaml/coff2yaml.cpp @@ -210,10 +210,7 @@ return YAMLObj; } -error_code coff2yaml(raw_ostream &Out, MemoryBuffer *Buff) { - error_code ec; - object::COFFObjectFile Obj(Buff, ec); - check(ec); +error_code coff2yaml(raw_ostream &Out, const object::COFFObjectFile &Obj) { COFFDumper Dumper(Obj); yaml::Output Yout(Out); Index: tools/obj2yaml/obj2yaml.h =================================================================== --- tools/obj2yaml/obj2yaml.h +++ tools/obj2yaml/obj2yaml.h @@ -13,10 +13,11 @@ #ifndef LLVM_TOOLS_OBJ2YAML_H #define LLVM_TOOLS_OBJ2YAML_H -#include "llvm/Support/MemoryBuffer.h" +#include "llvm/Object/COFF.h" #include "llvm/Support/raw_ostream.h" #include "llvm/Support/system_error.h" -llvm::error_code coff2yaml(llvm::raw_ostream &Out, llvm::MemoryBuffer *TheObj); +llvm::error_code coff2yaml(llvm::raw_ostream &Out, + const llvm::object::COFFObjectFile &Obj); #endif Index: tools/obj2yaml/obj2yaml.cpp =================================================================== --- tools/obj2yaml/obj2yaml.cpp +++ tools/obj2yaml/obj2yaml.cpp @@ -7,6 +7,7 @@ // //===----------------------------------------------------------------------===// +#include "Error.h" #include "obj2yaml.h" #include "llvm/Object/Archive.h" #include "llvm/Object/COFF.h" @@ -16,16 +17,30 @@ #include "llvm/Support/Signals.h" using namespace llvm; +using namespace llvm::object; -namespace { -enum ObjectFileType { - coff -}; +static error_code dumpObject(const ObjectFile &Obj) { + if (Obj.isCOFF()) + return coff2yaml(outs(), cast(Obj)); + + return obj2yaml_error::unsupported_obj_file_format; } -cl::opt InputFormat( - cl::desc("Choose input format"), - cl::values(clEnumVal(coff, "process COFF object files"), clEnumValEnd)); +static error_code dumpInput(StringRef File) { + if (File != "-" && !sys::fs::exists(File)) + return obj2yaml_error::file_not_found; + + ErrorOr BinaryOrErr = createBinary(File); + if (error_code EC = BinaryOrErr.getError()) + return EC; + + std::unique_ptr Binary(BinaryOrErr.get()); + // TODO: If this is an archive, then burst it and dump each entry + if (ObjectFile *Obj = dyn_cast(Binary.get())) + return dumpObject(*Obj); + + return obj2yaml_error::unrecognized_file_format; +} cl::opt InputFilename(cl::Positional, cl::desc(""), cl::init("-")); @@ -36,17 +51,9 @@ PrettyStackTraceProgram X(argc, argv); llvm_shutdown_obj Y; // Call llvm_shutdown() on exit. - // Process the input file - std::unique_ptr buf; - - // TODO: If this is an archive, then burst it and dump each entry - if (error_code ec = MemoryBuffer::getFileOrSTDIN(InputFilename, buf)) { - errs() << "Error: '" << ec.message() << "' opening file '" << InputFilename - << "'\n"; - } else { - ec = coff2yaml(outs(), buf.release()); - if (ec) - errs() << "Error: " << ec.message() << " dumping COFF file\n"; + if (error_code EC = dumpInput(InputFilename)) { + errs() << "Error: '" << EC.message() << "'\n"; + return 1; } return 0;