CheckIPCVisitor.h 3.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899
  1. // Copyright (c) 2016 The Chromium Authors. All rights reserved.
  2. // Use of this source code is governed by a BSD-style license that can be
  3. // found in the LICENSE file.
  4. // This check ensures that 32/64-bit unstable types are not used in IPC.
  5. //
  6. // A type (or typedef) is unstable if it changes size between 32/ 64-bit
  7. // platforms. However, it's impossible to accurately identify unstable
  8. // typedefs, because their definitions rely on the preprocessor. For
  9. // example uintptr_t is either unsigned int or unsigned long.
  10. //
  11. // So we're not trying to be accurate, and just blacklisting some types
  12. // that are known to be unstable:
  13. // 1. Types: long / unsigned long (but not typedefs to)
  14. // 2. Typedefs: intmax_t, uintmax_t, intptr_t, uintptr_t, wint_t,
  15. // size_t, rsize_t, ssize_t, ptrdiff_t, dev_t, off_t, clock_t,
  16. // time_t, suseconds_t (including typedefs to)
  17. //
  18. // Additionally, templates referencing blacklisted types (e.g. vector<long>)
  19. // are also blacklisted.
  20. //
  21. // Blacklisted types are checked in:
  22. // 1. IPC::WriteParam() calls
  23. // 2. IPC::CheckedTuple<> specializations
  24. //
  25. #ifndef TOOLS_CLANG_PLUGINS_CHECKIPC_VISITOR_H_
  26. #define TOOLS_CLANG_PLUGINS_CHECKIPC_VISITOR_H_
  27. #include <vector>
  28. #include "clang/AST/AST.h"
  29. #include "clang/AST/ASTConsumer.h"
  30. #include "clang/AST/RecursiveASTVisitor.h"
  31. #include "clang/Frontend/CompilerInstance.h"
  32. #include "llvm/ADT/StringSet.h"
  33. namespace chrome_checker {
  34. class CheckIPCVisitor {
  35. public:
  36. explicit CheckIPCVisitor(clang::CompilerInstance& compiler);
  37. void set_context(clang::ASTContext* context) { context_ = context; }
  38. void BeginDecl(clang::Decl* decl);
  39. void EndDecl();
  40. void VisitTemplateSpecializationType(
  41. clang::TemplateSpecializationType* spec);
  42. void VisitCallExpr(clang::CallExpr* call_expr);
  43. private:
  44. // ValidateXXX functions return false if validation failed and diagnostic
  45. // was reported. They return true otherwise (not applicable / validation
  46. // succeeded).
  47. bool ValidateWriteParam(const clang::CallExpr* call_expr);
  48. bool ValidateWriteParamSignature(const clang::CallExpr* call_expr);
  49. bool ValidateWriteParamArgument(const clang::Expr* arg_expr);
  50. bool ValidateCheckedTuple(
  51. const clang::TemplateSpecializationType* spec);
  52. template <typename T>
  53. const T* GetParentDecl() const;
  54. bool IsBlacklistedType(clang::QualType type) const;
  55. bool IsBlacklistedTypedef(const clang::TypedefNameDecl* tdef) const;
  56. struct CheckDetails {
  57. clang::QualType entry_type;
  58. clang::QualType exit_type;
  59. llvm::SmallVector<const clang::TypedefType*, 5> typedefs;
  60. };
  61. bool CheckType(clang::QualType type, CheckDetails* details) const;
  62. bool CheckIntegerType(clang::QualType type, CheckDetails* details) const;
  63. bool CheckTemplateArgument(const clang::TemplateArgument& arg,
  64. CheckDetails* details) const;
  65. void ReportCheckError(const CheckDetails& details,
  66. clang::SourceLocation loc,
  67. unsigned error);
  68. clang::CompilerInstance& compiler_;
  69. clang::ASTContext* context_;
  70. unsigned error_write_param_bad_type_;
  71. unsigned error_tuple_bad_type_;
  72. unsigned error_write_param_bad_signature_;
  73. unsigned note_see_here_;
  74. std::vector<const clang::Decl*> decl_stack_;
  75. llvm::StringSet<> blacklisted_typedefs_;
  76. };
  77. } // namespace chrome_checker
  78. #endif // TOOLS_CLANG_PLUGINS_CHECKIPC_VISITOR_H_