Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add Varied analysis to the reverse mode #1084

Open
wants to merge 14 commits into
base: master
Choose a base branch
from

Conversation

ovdiiuv
Copy link
Collaborator

@ovdiiuv ovdiiuv commented Sep 6, 2024

This PR adds Varied analysis support in the reverse mode, fixes wrong jacobian results and updates tests.

Copy link

codecov bot commented Sep 6, 2024

Codecov Report

Attention: Patch coverage is 96.06742% with 7 lines in your changes missing coverage. Please review.

Project coverage is 94.31%. Comparing base (b414202) to head (59ea27e).
Report is 11 commits behind head on master.

Files with missing lines Patch % Lines
lib/Differentiator/DiffPlanner.cpp 88.00% 3 Missing ⚠️
tools/ClangPlugin.h 70.00% 3 Missing ⚠️
lib/Differentiator/ActivityAnalyzer.cpp 99.12% 1 Missing ⚠️
Additional details and impacted files

Impacted file tree graph

@@            Coverage Diff             @@
##           master    #1084      +/-   ##
==========================================
+ Coverage   94.25%   94.31%   +0.06%     
==========================================
  Files          55       57       +2     
  Lines        8445     8608     +163     
==========================================
+ Hits         7960     8119     +159     
- Misses        485      489       +4     
Files with missing lines Coverage Δ
include/clad/Differentiator/CladConfig.h 100.00% <ø> (ø)
include/clad/Differentiator/DiffPlanner.h 72.00% <100.00%> (+2.43%) ⬆️
lib/Differentiator/ActivityAnalyzer.h 100.00% <100.00%> (ø)
lib/Differentiator/ReverseModeVisitor.cpp 97.77% <100.00%> (-0.08%) ⬇️
tools/ClangPlugin.cpp 95.70% <100.00%> (+0.12%) ⬆️
lib/Differentiator/ActivityAnalyzer.cpp 99.12% <99.12%> (ø)
lib/Differentiator/DiffPlanner.cpp 98.15% <88.00%> (-0.63%) ⬇️
tools/ClangPlugin.h 90.27% <70.00%> (-1.70%) ⬇️

... and 4 files with indirect coverage changes

Files with missing lines Coverage Δ
include/clad/Differentiator/CladConfig.h 100.00% <ø> (ø)
include/clad/Differentiator/DiffPlanner.h 72.00% <100.00%> (+2.43%) ⬆️
lib/Differentiator/ActivityAnalyzer.h 100.00% <100.00%> (ø)
lib/Differentiator/ReverseModeVisitor.cpp 97.77% <100.00%> (-0.08%) ⬇️
tools/ClangPlugin.cpp 95.70% <100.00%> (+0.12%) ⬆️
lib/Differentiator/ActivityAnalyzer.cpp 99.12% <99.12%> (ø)
lib/Differentiator/DiffPlanner.cpp 98.15% <88.00%> (-0.63%) ⬇️
tools/ClangPlugin.h 90.27% <70.00%> (-1.70%) ⬇️

... and 4 files with indirect coverage changes

Copy link
Contributor

@github-actions github-actions bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

clang-tidy made some suggestions

There were too many comments to post at once. Showing the first 10 out of 29. Check the log or trigger a new build to see more.

@@ -55,6 +60,7 @@ struct DiffRequest {
bool VerboseDiags = false;
/// A flag to enable TBR analysis during reverse-mode differentiation.
bool EnableTBRAnalysis = false;
bool EnableActivityAnalysis = false;
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

warning: member variable 'EnableActivityAnalysis' has public visibility [cppcoreguidelines-non-private-member-variables-in-classes]

  bool EnableActivityAnalysis = false;
       ^

lib/Differentiator/ActivityAnalyzer.cpp Outdated Show resolved Hide resolved
lib/Differentiator/ActivityAnalyzer.cpp Outdated Show resolved Hide resolved
lib/Differentiator/ActivityAnalyzer.cpp Show resolved Hide resolved
lib/Differentiator/ActivityAnalyzer.cpp Outdated Show resolved Hide resolved
lib/Differentiator/ActivityAnalyzer.cpp Outdated Show resolved Hide resolved
lib/Differentiator/ActivityAnalyzer.cpp Outdated Show resolved Hide resolved
return curBranch.find(VD) != curBranch.end();
}

void VariedAnalyzer::merge(VarsData* targetData, VarsData* mergeData) {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

warning: method 'merge' can be made static [readability-convert-member-functions-to-static]

lib/Differentiator/ActivityAnalyzer.h:77:

-     void merge(VarsData* targetData, VarsData* mergeData);
+     static void merge(VarsData* targetData, VarsData* mergeData);

Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is a good suggestion.

lib/Differentiator/ActivityAnalyzer.cpp Outdated Show resolved Hide resolved
lib/Differentiator/ActivityAnalyzer.cpp Outdated Show resolved Hide resolved
Copy link
Contributor

@github-actions github-actions bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

clang-tidy made some suggestions

There were too many comments to post at once. Showing the first 10 out of 16. Check the log or trigger a new build to see more.

// Set current block ID to the ID of entry the block.
auto* entry = &m_CFG->getEntry();
m_CurBlockID = entry->getBlockID();
m_BlockData[m_CurBlockID] = new VarsData();
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

warning: assigning newly created 'gsl::owner<>' to non-owner 'value_type' (aka 'clad::VariedAnalyzer::VarsData *') [cppcoreguidelines-owning-memory]

  m_BlockData[m_CurBlockID] = new VarsData();
  ^

return curBranch.find(VD) != curBranch.end();
}

void VariedAnalyzer::merge(VarsData* targetData, VarsData* mergeData) {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

warning: method 'merge' can be made static [readability-convert-member-functions-to-static]

lib/Differentiator/ActivityAnalyzer.h:72:

-   void merge(VarsData* targetData, VarsData* mergeData);
+   static void merge(VarsData* targetData, VarsData* mergeData);

lib/Differentiator/ActivityAnalyzer.cpp Outdated Show resolved Hide resolved
lib/Differentiator/ActivityAnalyzer.h Show resolved Hide resolved
lib/Differentiator/ActivityAnalyzer.h Show resolved Hide resolved
lib/Differentiator/ActivityAnalyzer.h Outdated Show resolved Hide resolved
lib/Differentiator/ActivityAnalyzer.h Outdated Show resolved Hide resolved
lib/Differentiator/ActivityAnalyzer.h Outdated Show resolved Hide resolved
lib/Differentiator/ActivityAnalyzer.h Outdated Show resolved Hide resolved
lib/Differentiator/ActivityAnalyzer.h Outdated Show resolved Hide resolved
Copy link
Contributor

@github-actions github-actions bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

clang-tidy made some suggestions

There were too many comments to post at once. Showing the first 10 out of 18. Check the log or trigger a new build to see more.

lib/Differentiator/ActivityAnalyzer.cpp Outdated Show resolved Hide resolved
lib/Differentiator/ActivityAnalyzer.cpp Outdated Show resolved Hide resolved
lib/Differentiator/ActivityAnalyzer.cpp Outdated Show resolved Hide resolved
lib/Differentiator/ActivityAnalyzer.cpp Show resolved Hide resolved
lib/Differentiator/ActivityAnalyzer.h Outdated Show resolved Hide resolved
lib/Differentiator/ActivityAnalyzer.h Outdated Show resolved Hide resolved
lib/Differentiator/ActivityAnalyzer.h Outdated Show resolved Hide resolved
lib/Differentiator/ActivityAnalyzer.h Outdated Show resolved Hide resolved
lib/Differentiator/ActivityAnalyzer.h Outdated Show resolved Hide resolved
lib/Differentiator/ActivityAnalyzer.h Outdated Show resolved Hide resolved
Copy link
Contributor

@github-actions github-actions bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

clang-tidy made some suggestions

lib/Differentiator/ActivityAnalyzer.cpp Outdated Show resolved Hide resolved
lib/Differentiator/ActivityAnalyzer.cpp Outdated Show resolved Hide resolved
lib/Differentiator/ActivityAnalyzer.h Outdated Show resolved Hide resolved
lib/Differentiator/ActivityAnalyzer.h Outdated Show resolved Hide resolved
lib/Differentiator/ActivityAnalyzer.h Outdated Show resolved Hide resolved
lib/Differentiator/ActivityAnalyzer.h Outdated Show resolved Hide resolved
lib/Differentiator/ActivityAnalyzer.h Outdated Show resolved Hide resolved
VarsData* varsData2);

void merge(VarsData* targetData, VarsData* mergeData);
ASTContext& m_Context;
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

warning: member 'm_Context' of type 'ASTContext &' is a reference [cppcoreguidelines-avoid-const-or-ref-data-members]

  ASTContext& m_Context;
              ^

lib/Differentiator/ReverseModeVisitor.cpp Outdated Show resolved Hide resolved
@ovdiiuv ovdiiuv force-pushed the activity branch 2 times, most recently from 65075a3 to df82648 Compare September 6, 2024 20:38
Copy link
Contributor

@github-actions github-actions bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

clang-tidy made some suggestions

lib/Differentiator/ActivityAnalyzer.cpp Show resolved Hide resolved
return true;
}

bool VariedAnalyzer::VisitCallExpr(CallExpr* CE) { return true; }
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

warning: method 'VisitCallExpr' can be made static [readability-convert-member-functions-to-static]

lib/Differentiator/ActivityAnalyzer.h:103:

-   bool VisitCallExpr(clang::CallExpr* CE);
+   static bool VisitCallExpr(clang::CallExpr* CE);

Copy link
Owner

@vgvassilev vgvassilev left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Here is a partial review. Please address the clang-tidy complaints as most of them are good. I'd also rely on @PetroZarytskyi here for a review.

m_BlockPassCounter.resize(m_CFG->size(), 0);

// Set current block ID to the ID of entry the block.
auto* entry = &m_CFG->getEntry();
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We should expand the type here.

lib/Differentiator/ActivityAnalyzer.cpp Outdated Show resolved Hide resolved
}
}

for (const auto succ : block.succs()) {
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We should expand the type here.

lib/Differentiator/ActivityAnalyzer.cpp Show resolved Hide resolved
lib/Differentiator/ActivityAnalyzer.cpp Outdated Show resolved Hide resolved
m_Varied = true;

if (const auto* VD = dyn_cast<VarDecl>(DRE->getDecl())) {
auto& curBranch = getCurBlockVarsData();
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We should expand the type here.

lib/Differentiator/ActivityAnalyzer.cpp Outdated Show resolved Hide resolved
lib/Differentiator/ActivityAnalyzer.cpp Show resolved Hide resolved
lib/Differentiator/ActivityAnalyzer.h Show resolved Hide resolved
lib/Differentiator/ActivityAnalyzer.h Outdated Show resolved Hide resolved
Copy link
Collaborator

@PetroZarytskyi PetroZarytskyi left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thank you for your work. I didn't mention pullbacks and call exprs because we already made huge progress there yesterday. Overall, the PR looks awesome. Its simplicity makes me feel that TBR was overcomplicated. I think we made the right decision to start with a simplified implementation.

lib/Differentiator/ActivityAnalyzer.h Outdated Show resolved Hide resolved
lib/Differentiator/ActivityAnalyzer.cpp Outdated Show resolved Hide resolved
lib/Differentiator/ActivityAnalyzer.cpp Show resolved Hide resolved
lib/Differentiator/ActivityAnalyzer.h Outdated Show resolved Hide resolved
lib/Differentiator/ReverseModeVisitor.cpp Show resolved Hide resolved
test/Analyses/ActivityReverse.cpp Outdated Show resolved Hide resolved
Copy link
Contributor

@github-actions github-actions bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

clang-tidy made some suggestions

// Set current block ID to the ID of entry the block.
auto* entry = &m_CFG->getEntry();
m_CurBlockID = entry->getBlockID();
m_BlockData[m_CurBlockID] = new VarsData();
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

warning: assigning newly created 'gsl::owner<>' to non-owner 'value_type' (aka 'std::set<const clang::VarDecl *> *') [cppcoreguidelines-owning-memory]

  m_BlockData[m_CurBlockID] = new VarsData();
  ^

auto& succData = m_BlockData[succ->getBlockID()];

if (!succData)
succData = new VarsData(*m_BlockData[block.getBlockID()]);
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

warning: assigning newly created 'gsl::owner<>' to non-owner 'value_type' (aka 'std::set<const clang::VarDecl *> *') [cppcoreguidelines-owning-memory]

      succData = new VarsData(*m_BlockData[block.getBlockID()]);
      ^

lib/Differentiator/ActivityAnalyzer.cpp Outdated Show resolved Hide resolved
return curBranch.find(VD) != curBranch.end();
}

void VariedAnalyzer::merge(VarsData* targetData, VarsData* mergeData) {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

warning: method 'merge' can be made static [readability-convert-member-functions-to-static]

lib/Differentiator/ActivityAnalyzer.h:28:

-   void merge(VarsData* targetData, VarsData* mergeData);
+   static void merge(VarsData* targetData, VarsData* mergeData);

lib/Differentiator/ActivityAnalyzer.cpp Outdated Show resolved Hide resolved
lib/Differentiator/ActivityAnalyzer.h Show resolved Hide resolved
Copy link
Contributor

@github-actions github-actions bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

clang-tidy made some suggestions

lib/Differentiator/ActivityAnalyzer.h Show resolved Hide resolved

std::set<const clang::VarDecl*>& m_VariedDecls;
using VarsData = std::set<const clang::VarDecl*>;
VarsData* createNewVarsData(VarsData toAssign) {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

warning: method 'createNewVarsData' can be made static [readability-convert-member-functions-to-static]

Suggested change
VarsData* createNewVarsData(VarsData toAssign) {
static VarsData* createNewVarsData(VarsData toAssign) {

std::set<const clang::VarDecl*>& m_VariedDecls;
using VarsData = std::set<const clang::VarDecl*>;
VarsData* createNewVarsData(VarsData toAssign) {
return new VarsData(toAssign);
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

warning: parameter 'toAssign' is passed by value and only copied once; consider moving it to avoid unnecessary copies [performance-unnecessary-value-param]

lib/Differentiator/ActivityAnalyzer.h:13:

+ #include <utility>
Suggested change
return new VarsData(toAssign);
return new VarsData(std::move(toAssign));

std::set<const clang::VarDecl*>& m_VariedDecls;
using VarsData = std::set<const clang::VarDecl*>;
VarsData* createNewVarsData(VarsData toAssign) {
return new VarsData(toAssign);
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

warning: returning a newly created resource of type 'VarsData *' (aka 'set<const clang::VarDecl *> *') or 'gsl::owner<>' from a function whose return type is not 'gsl::owner<>' [cppcoreguidelines-owning-memory]

    return new VarsData(toAssign);
    ^

Copy link
Owner

@vgvassilev vgvassilev left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Please check the resolved conversations as some are not really resolved by adding the requested change.

lib/Differentiator/ActivityAnalyzer.cpp Show resolved Hide resolved
Copy link
Contributor

@github-actions github-actions bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

clang-tidy made some suggestions

lib/Differentiator/ActivityAnalyzer.h Show resolved Hide resolved
lib/Differentiator/ActivityAnalyzer.h Show resolved Hide resolved
return curBranch.find(VD) != curBranch.end();
}

void VariedAnalyzer::merge(VarsData* targetData, VarsData* mergeData) {
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is a good suggestion.

test/Jacobian/FunctionCalls.C Outdated Show resolved Hide resolved
lib/Differentiator/ActivityAnalyzer.cpp Outdated Show resolved Hide resolved
lib/Differentiator/ActivityAnalyzer.h Show resolved Hide resolved
lib/Differentiator/ActivityAnalyzer.h Outdated Show resolved Hide resolved
lib/Differentiator/ActivityAnalyzer.h Show resolved Hide resolved
lib/Differentiator/ActivityAnalyzer.h Outdated Show resolved Hide resolved
lib/Differentiator/CMakeLists.txt Outdated Show resolved Hide resolved
lib/Differentiator/DiffPlanner.cpp Outdated Show resolved Hide resolved
lib/Differentiator/ActivityAnalyzer.cpp Outdated Show resolved Hide resolved
lib/Differentiator/ActivityAnalyzer.cpp Outdated Show resolved Hide resolved
lib/Differentiator/ActivityAnalyzer.cpp Outdated Show resolved Hide resolved
Copy link
Contributor

@github-actions github-actions bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

clang-tidy made some suggestions

There were too many comments to post at once. Showing the first 10 out of 26. Check the log or trigger a new build to see more.

@@ -7,6 +7,11 @@
#include "clad/Differentiator/DynamicGraph.h"
#include "clad/Differentiator/ParseDiffArgsTypes.h"

<<<<<<< HEAD
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

warning: version control conflict marker in file [clang-diagnostic-error]

<<<<<<< HEAD
^

lib/Differentiator/ActivityAnalyzer.cpp Show resolved Hide resolved
lib/Differentiator/ActivityAnalyzer.cpp Outdated Show resolved Hide resolved
m_Varied = false;
TraverseStmt(R);
m_Marking = m_Varied;
TraverseStmt(L);
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

warning: cannot initialize object parameter of type 'clang::RecursiveASTVisitorclad::VariedAnalyzer' with an expression of type 'clad::VariedAnalyzer' [clang-diagnostic-error]

    TraverseStmt(L);
    ^

TraverseStmt(L);
m_Marking = false;
} else {
TraverseStmt(L);
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

warning: cannot initialize object parameter of type 'clang::RecursiveASTVisitorclad::VariedAnalyzer' with an expression of type 'clad::VariedAnalyzer' [clang-diagnostic-error]

    TraverseStmt(L);
    ^

m_Marking = false;
} else {
TraverseStmt(L);
TraverseStmt(R);
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

warning: cannot initialize object parameter of type 'clang::RecursiveASTVisitorclad::VariedAnalyzer' with an expression of type 'clad::VariedAnalyzer' [clang-diagnostic-error]

    TraverseStmt(R);
    ^

lib/Differentiator/ActivityAnalyzer.cpp Show resolved Hide resolved
lib/Differentiator/ActivityAnalyzer.cpp Show resolved Hide resolved
@ovdiiuv ovdiiuv force-pushed the activity branch 2 times, most recently from 23e0923 to 792cd6b Compare September 13, 2024 18:47
/// statements in the reverse mode, improving generated codes efficiency.
namespace clad {
using VarsData = std::set<const clang::VarDecl*>;
static inline void mergeVarsData(VarsData* targetData, VarsData* mergeData) {
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This function should go in the cpp file.

@vgvassilev
Copy link
Owner

Can you rebase this PR?

Comment on lines 133 to 139
if (isVaried(dyn_cast<VarDecl>(DRE->getDecl())))
m_Varied = true;

if (const auto* VD = dyn_cast<VarDecl>(DRE->getDecl())) {
if (m_Varied && m_Marking)
copyVarToCurBlock(VD);
}
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
if (isVaried(dyn_cast<VarDecl>(DRE->getDecl())))
m_Varied = true;
if (const auto* VD = dyn_cast<VarDecl>(DRE->getDecl())) {
if (m_Varied && m_Marking)
copyVarToCurBlock(VD);
}
VarDecl *VD = dyn_cast<VarDecl>(DRE->getDecl());
if (!VD)
return true;
if (isVaried(VD))
m_Varied = true;
if (m_Varied && m_Marking)
copyVarToCurBlock(VD);

Comment on lines 46 to 52
std::unique_ptr<clang::CFG> m_CFG;
std::vector<std::unique_ptr<VarsData>> m_BlockData;
unsigned m_CurBlockID{};
std::set<unsigned> m_CFGQueue;
bool isVaried(const clang::VarDecl* VD) const;
void copyVarToCurBlock(const clang::VarDecl* VD);
VarsData& getCurBlockVarsData() { return *m_BlockData[m_CurBlockID]; }
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We need documentation here, too.

VariedAnalyzer& operator=(const VariedAnalyzer&&) = delete;

/// Runs Varied analysis.
/// \param FD Function to run the analysis on.
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
/// \param FD Function to run the analysis on.
/// \param[in] FD Function to run the analysis on.

std::set<const clang::VarDecl*>& m_VariedDecls;
// using VarsData = std::set<const clang::VarDecl*>;
/// A helper method to allocate VarsData
/// \param toAssign - Parameter to initialize new VarsData with.
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
/// \param toAssign - Parameter to initialize new VarsData with.
/// \param toAssign[in] - Parameter to initialize new VarsData with.

Copy link
Contributor

@github-actions github-actions bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

clang-tidy made some suggestions

auto& succData = m_BlockData[succ->getBlockID()];

if (!succData) {
succData = new VarsData(*m_BlockData[block.getBlockID()]);
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

warning: no viable overloaded '=' [clang-diagnostic-error]

      succData = new VarsData(*m_BlockData[block.getBlockID()]);
               ^
Additional context

/usr/include/c++/12/bits/unique_ptr.h:405: candidate function not viable: no known conversion from 'VarsData *' (aka 'set<const clang::VarDecl *> *') to 'unique_ptr<set<const VarDecl *>>' for 1st argument

      unique_ptr& operator=(unique_ptr&&) = default;
                  ^

/usr/include/c++/12/bits/unique_ptr.h:421: candidate template ignored: could not match 'unique_ptr<_Up, _Ep>' against 'VarsData *' (aka 'set<const clang::VarDecl *> *')

	operator=(unique_ptr<_Up, _Ep>&& __u) noexcept
 ^

/usr/include/c++/12/bits/unique_ptr.h:431: candidate function not viable: no known conversion from 'VarsData *' (aka 'set<const clang::VarDecl *> *') to 'nullptr_t' (aka 'std::nullptr_t') for 1st argument

      operator=(nullptr_t) noexcept
      ^

/usr/include/c++/12/bits/unique_ptr.h:514: candidate function not viable: no known conversion from 'VarsData *' (aka 'set<const clang::VarDecl *> *') to 'const unique_ptr<set<const VarDecl *>>' for 1st argument

      unique_ptr& operator=(const unique_ptr&) = delete;
                  ^


if (!succData) {
succData = new VarsData(*m_BlockData[block.getBlockID()]);
succData->m_Prev = m_BlockData[block.getBlockID()];
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

warning: no member named 'm_Prev' in 'std::set<const clang::VarDecl *>' [clang-diagnostic-error]

      succData->m_Prev = m_BlockData[block.getBlockID()];
                ^

return true;
}

bool VariedAnalyzer::VisitConditionalOperator(clang::ConditionalOperator* CO) {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

warning: method 'VisitConditionalOperator' can be made static [readability-convert-member-functions-to-static]

lib/Differentiator/ActivityAnalyzer.h:77:

-   bool VisitConditionalOperator(clang::ConditionalOperator* CO);
+   static bool VisitConditionalOperator(clang::ConditionalOperator* CO);

bool VisitUnaryOperator(clang::UnaryOperator* UnOp);
};
} // namespace clad
#endif // CLAD_DIFFERENTIATOR_ACTIVITYANALYZER_H
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

warning: #endif without #if [clang-diagnostic-error]

#endif // CLAD_DIFFERENTIATOR_ACTIVITYANALYZER_H
 ^

@@ -2939,7 +2939,7 @@ Expr* getArraySizeExpr(const ArrayType* AT, ASTContext& context,

VarDecl* VDClone = nullptr;
Expr* derivedVDE = nullptr;
if (VDDerived)
if (VDDerived && m_DiffReq.shouldHaveAdjoint(const_cast<VarDecl*>(VD)))
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

warning: do not use const_cast [cppcoreguidelines-pro-type-const-cast]

    if (VDDerived && m_DiffReq.shouldHaveAdjoint(const_cast<VarDecl*>(VD)))
                                                 ^

@@ -2995,8 +2995,15 @@
VDDerived->setInitStyle(VarDecl::InitializationStyle::CInit);
}
}
if (!m_DiffReq.shouldHaveAdjoint(const_cast<VarDecl*>(VD))) {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

warning: do not use const_cast [cppcoreguidelines-pro-type-const-cast]

    if (!m_DiffReq.shouldHaveAdjoint(const_cast<VarDecl*>(VD))) {
                                     ^

Copy link
Contributor

@github-actions github-actions bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

clang-tidy made some suggestions

for (std::size_t i = 0, e = CE->getNumArgs(); i != e; ++i) {
clang::Expr* par = CE->getArg(i);
TraverseStmt(par);
if (m_Varied || 1) {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

warning: converting integer literal to bool, use bool literal instead [modernize-use-bool-literals]

Suggested change
if (m_Varied || 1) {
if (m_Varied || true) {

Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This probably should change to what it was before.

return true;
}

bool VariedAnalyzer::VisitInitListExpr(InitListExpr* ILE) { return true; }
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

warning: method 'VisitInitListExpr' can be made static [readability-convert-member-functions-to-static]

lib/Differentiator/ActivityAnalyzer.h:81:

-   bool VisitInitListExpr(clang::InitListExpr* ILE);
+   static bool VisitInitListExpr(clang::InitListExpr* ILE);

@@ -0,0 +1,85 @@
#ifndef CLAD_DIFFERENTIATOR_ACTIVITYANALYZER_H
#define CLAD_DIFFERENTIATOR_ACTIVITYANALYZER_H
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

warning: header guard does not follow preferred style [llvm-header-guard]

Suggested change
#define CLAD_DIFFERENTIATOR_ACTIVITYANALYZER_H
#ifndef GITHUB_WORKSPACE_LIB_DIFFERENTIATOR_ACTIVITYANALYZER_H
#define GITHUB_WORKSPACE_LIB_DIFFERENTIATOR_ACTIVITYANALYZER_H

lib/Differentiator/ActivityAnalyzer.h:84:

- #endif // CLAD_DIFFERENTIATOR_ACTIVITYANALYZER_H
+ #endif // GITHUB_WORKSPACE_LIB_DIFFERENTIATOR_ACTIVITYANALYZER_H


bool VariedAnalyzer::VisitDeclStmt(DeclStmt* DS) {
for (Decl* D : DS->decls()) {
if (!isa<VarDecl>(D))
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

A test here could be class C{} c; that produces a DeclStmt whose Stmt is not a VarDecl.

Copy link
Contributor

@github-actions github-actions bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

clang-tidy made some suggestions

@@ -55,6 +62,7 @@ struct DiffRequest {
bool VerboseDiags = false;
/// A flag to enable TBR analysis during reverse-mode differentiation.
bool EnableTBRAnalysis = false;
bool EnableVariedAnalysis = false;
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

warning: member variable 'EnableVariedAnalysis' has public visibility [cppcoreguidelines-non-private-member-variables-in-classes]

  bool EnableVariedAnalysis = false;
       ^


bool VariedAnalyzer::VisitCallExpr(CallExpr* CE) {
FunctionDecl* FD = CE->getDirectCallee();
bool noHiddenParam = 1;
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

warning: converting integer literal to bool, use bool literal instead [modernize-use-bool-literals]

Suggested change
bool noHiddenParam = 1;
bool noHiddenParam = true;

return true;
}

bool VariedAnalyzer::VisitInitListExpr(InitListExpr* ILE) { return true; }
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

warning: method 'VisitInitListExpr' can be made static [readability-convert-member-functions-to-static]

lib/Differentiator/ActivityAnalyzer.h:79:

-   bool VisitInitListExpr(clang::InitListExpr* ILE);
+   static bool VisitInitListExpr(clang::InitListExpr* ILE);

Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

ping.

if (isVaried(dyn_cast<VarDecl>(DRE->getDecl())))
m_Varied = true;

VarDecl* VD = dyn_cast<VarDecl>(DRE->getDecl());
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

warning: use auto when initializing with a template cast to avoid duplicating the type name [modernize-use-auto]

Suggested change
VarDecl* VD = dyn_cast<VarDecl>(DRE->getDecl());
auto* VD = dyn_cast<VarDecl>(DRE->getDecl());

lib/Differentiator/ActivityAnalyzer.h Show resolved Hide resolved
/// in a differentiable way. That result enables us to remove redundant
/// statements in the reverse mode, improving generated codes efficiency.
namespace clad {
using VarsData = std::set<const clang::VarDecl*>;
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This can go in the class definition.

/// By performing static data-flow analysis, so called Varied variables
/// are determined, meaning variables that depend on input parameters
/// in a differentiable way. That result enables us to remove redundant
/// statements in the reverse mode, improving generated codes efficiency.
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The documentation should go to the class definition.

return true;
}

bool VariedAnalyzer::VisitInitListExpr(InitListExpr* ILE) { return true; }
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

ping.

@@ -40,6 +40,8 @@ void fn1(double i, double j, double* output) {
// CHECK-NEXT: }
// CHECK-NEXT: }



Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Redundant new lines.

@@ -998,7 +998,7 @@ double sq_defined_later(double x) {
// CHECK-NEXT: *_d_b += _d_y;
// CHECK-NEXT: }

// CHECK: void do_nothing_pullback(double *u, double *v, double *w, double _d_y, double *_d_u, double *_d_v, double *_d_w) {
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Why did we need this change?

@@ -441,14 +441,14 @@ double do_nothing(double* u, double* v, double* w) {
return u[0];
}

// CHECK: void do_nothing_pullback(double *u, double *v, double *w, double _d_y, double *_d_u, double *_d_v, double *_d_w);
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Why this change was needed?

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We used to remove non varied parameters from the adjoint, but it'd crash cms example, so I removed it for now.

} else if (opCode == BO_Add || opCode == BO_Sub || opCode == BO_Mul ||
opCode == BO_Div) {
for (auto* subexpr : BinOp->children())
if (!isa<BinaryOperator>(subexpr))
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Why don't we visit binary operators recursively? Doesn't this mean we will ignore a part of x + y + z for example? Since it's treated as a nested addition operation in the AST.

Copy link
Collaborator Author

@ovdiiuv ovdiiuv Oct 6, 2024

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

See #1106

if (opCode == UO_AddrOf || opCode == UO_Deref) {
m_Varied = true;
m_Marking = true;
}
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Why do we need to set these modes to true here? And even if so, shouldn't we also set m_Marking to false afterward?


bool VariedAnalyzer::VisitDeclRefExpr(DeclRefExpr* DRE) {
if (isVaried(dyn_cast<VarDecl>(DRE->getDecl())))
m_Varied = true;
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Doesn't this portion of the code repeat what comes next? Perhaps we should keep one of these.

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

yes

targetData->insert(i);
for (const clang::VarDecl* i : *targetData)
mergeData->insert(i);
}
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It looks like this function will make targetData and mergeData identical. Do we need them both to be modified? Even if we do, we can probably do *mergedata = *targetdata instead of the last two lines.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

3 participants