AnalysisUsage error in llvm - llvm

This is what im getting when I'm trying to use DomFrontier information from my pass:
opt: /home/smriti/Thesis/llvm/include/llvm/PassAnalysisSupport.h:214:
AnalysisType && llvm::Pass::getAnalysisID(AnalysisID) const [AnalysisType = llvm::DominanceFrontier]:
Assertion `ResultPass && "getAnalysis*() called on an analysis that was not " "'required' by pass!"' failed`
I've put this within my pass which derives from the module pass:
virtual void getAnalysisUsage(AnalysisUsage &AU) const {AU.addRequired<DominanceFrontier>();}
And my runOnFunction contains the following:
DominanceFrontier& DF = getAnalysis<DominanceFrontier>(FF);
Please let me know if I have problem with these? Or should I attach the entire code of the pass if the problem is somewhere else?

Related

Mock call not being detected

I created a test case with Catch2 and I am trying to use TrompeLoeil for finer testing.
However the mock calls either don't happen at all, or happen but don't seem to be detecting by the framework.
Here is a minimal reproductible example :
class MyRealClass
{
public:
virtual int returnSumOfValues(int a, int b)
{
return a + b;
}
};
class MyMockClass : public MyRealClass
{
public:
MAKE_MOCK2(returnSumOfValues, int(int,int));
};
class MyTestedClass
{
public:
MyTestedClass(MyRealClass* _computeObj)
: computeObj(_computeObj)
{
}
int compute()
{
return computeObj->returnSumOfValues(2,3);
}
MyRealClass* computeObj;
};
TEST_CASE("Testing Trompe L'oeil")
{
auto mock = new MyMockClass();
MyTestedClass testedClass(mock);
int val = testedClass.compute();
CHECK(val == 5);
REQUIRE_CALL(*mock, returnSumOfValues(2,3)).RETURN(5);
}
And here is the error I get from running this test :
------------------------------------------------------------------------------- Testing Trompe L'oeil
------------------------------------------------------------------------------- ../../../src/MEGAAutoTests/UnitTests/control/TransferBatchTests.cpp:164
...............................................................................
../../../src/MEGAAutoTests/UnitTests/main.cpp:38: FAILED: explicitly
with message: No match for call of returnSumOfValues with signature
int(int,int) with.
param _1 == 2
param _2 == 3
I debugged this step by step and the mocked returnSumOfValues() is the one being executed.
However, if I make MyRealClass::returnSumOfValues() not virtual, the mock class is not used at all.
And the error is :
------------------------------------------------------------------------------- Testing Trompe L'oeil
------------------------------------------------------------------------------- ../../../src/MEGAAutoTests/UnitTests/control/TransferBatchTests.cpp:164
...............................................................................
../../../src/MEGAAutoTests/UnitTests/main.cpp:43: FAILED: CHECK(
failure.empty() ) with expansion: false with message: failure :=
"../../../src/MEGAAutoTests/UnitTests/control/TransferBatchTests.
cpp:172 Unfulfilled expectation: Expected
*mock.returnSumOfValues(2,3) to be called once, actually never called
param _1 == 2
param _2 == 3 "
This seems to not be consistent with the official documentation, which states that :
The line MAKE_MOCK2(log, void(int severity, const std::string& msg))
creates a mock function void Logger::log(int, const std::string&). If
MAKE_MOCKn(...) or MAKE_CONST_MOCKn(...) are used to implement a
virtual function from a base class, it is always recommended to add a
third macro parameter override since it gives the compiler an ability
to complain about mistakes.
Recommended, not required. And to give the compiler more information, not to make the test work.
TL, DR
Why is my code sample not working?
Why do I need to make mocked functions virtual when the documentation suggests it is not mandatory?
The issue was that expectations need to be set beforehand.
I though they worked like assertions, checking a state after the code was executed, but this is not the case.
In this case, moving the call solved the problem. Here is the fixed code sample :
TEST_CASE("Testing Trompe L'oeil")
{
auto mock = new MyMockClass();
MyTestedClass testedClass(mock);
REQUIRE_CALL(*mock, returnSumOfValues(2,3)).RETURN(5);
int val = testedClass.compute();
CHECK(val == 5);
}
This is the solution to the first problem, the second one (only virtual functions can be mocked) remains unanswered.

assertEquals fails for Error implementation but pass for Success one

I have these sealed interface
sealed interface Result<out T> {
data class Success<T>(val data: T) : Result<T>
data class Error(val exception: Throwable? = null) : Result<Nothing>
}
when i tried to assertEquals the Success one, it pass. But when it comes to Error one, it will fail even though the content is identical. Here is simple example:
#Test
fun testSucess() = runTest {
whenever(repository.login("email", "password"))
.thenReturn(someValue)
val expected = Result.Success(data = someValue)
val actual = loginUseCase(LoginRequest("email", "password"))
verify(repository).login("email", "password")
assertEquals(expected, actual) // this will pass
}
#Test
fun testError() = runTest {
val exception = RuntimeException("HTTP Error")
whenever(repository.login("", ""))
.thenThrow(exception)
val expected = Result.Error(exception = exception)
val actual = loginUseCase(LoginRequest("", ""))
verify(repository).login("", "")
assertEquals(expected, actual) // this will fail
assertEquals(expected.toString(), actual.toString()) // this will pass
}
What is causing this and what is possible solution to this? I have read some info that it needs equals() to be overriden, but i still confused as to why it only happens in Error case only and how to properly override the equals method.
Data classes in Kotlin have an implicitly generated equals function automatically derived from all their properties.
The problem you are facing is probably due to the fact that the type of your someValue has a proper equals function, so the equals works for your Success and its property value. But Throwable does not have an equals function which means that two Throwables are only equal if they are the same instance, which is obviously not the case for expected and actual in your test assertion. I can only guess that in loginUseCase, the exception is wrapped inside another exception, or a new exception is created based on the one thrown by the repository?
Kotlin already has a built-in Result type, and I strongly recommend using that one instead of defining your own.
Nonetheless, if you use the built-in type, you will probably face the same problem, since the equals check still fails for the different exception instances.
There are several ways to solve that:
Define your own exception type and override the equals function to return true if they are both of the same type and have the same message.
Check for expected is Error (or with the default Result type that expected.isFailure), and then check that the messages are the same.
Make sure that loginUseCase throws exactly the same exception instance as is thrown by the repository.

Writing a unit test in gtest for a function returning an nlohmann::json object

This is my function that I would like to create a test for:
static nlohmann::json parse_json(const std::string& file_path)
{
std::ifstream i(file_path);
nlohmann::json j = nlohmann::json::parse(i);
return j;
}
I understand this type of test:
TEST(FactorialTest, HandlesZeroInput) {
EXPECT_EQ(Factorial(0), 1);
}
But when my function is returning an object I'm not exactly sure how to accomplish this. Is this where mocking comes into play?
Where I would need to write something like this:
class fakeJsonObject {
public:
MOCK_METHOD(nlohmann::json, parse_json, std::string& file_path);
};
Then create a test with my mocked object and compare it to an object created from my parse_json function?
General answer : a good unit test follow the rule AAA
Arrange : place where you prepare things that will be tested
Act : function call under test
Assert : Assert that the function call gives you the right result.
So in your case you have to prepare / or better generate a file containing json data. (Arrange).
Call the function. (Act)
Assert you got a nlhohmann::json object which is related to the json data contained in the file.(Assert)

How to break private method call from a Method Under Test in Microsoft Fakes Unit Testing?

I tried for searching a lot regarding this but did not find any helpful information. And I'm stuck in below situation and seeking for help.
Below is my method which I want to test:
public void MethodToTest()
{
this._app = this.GetApp(out this._pId);
}
//here beelow method which is from the same class and private
private Microsoft.Office.Interop.Word.Application GetApp(out int processId)
{
//some code which returns Application
}
Now I dont want to execute this method instead I want to shim this method
using
ShimMyclassName.Allinstances.set_GetAppInt32Out = () => my expected output
But compiler is throwing error:
cannot assign to set_GetAppInt32Out because it's a method group.
So I tried to changed it to:
ShimMyclassName.Allinstances.set_GetAppInt32Out( here it is expecting some out delegate like (OutFunc<WordApplication, int, Microsoft.office.Interop.Word.Application> Value)
In ShimMyClass below is the signature:
public void set_GetAppInt32Out(object value);
So I'm stuck here. How can I pass the value and How I can Break the private method call and expect it to return my expected output instead of executing the original private method?

How test SqlParameter for equality

Using NUnit and NMock2 I was not able to compare what I thought were the same SqlParameters:
SqlParameter param1 = new SqlParameter("#Id", 1);
SqlParameter param2 = new SqlParameter("#Id", 1);
Assert.IsTrue(param1.Equals(param2)); // This failed
I stumbled across this problem, when trying to test an execution of a method using NMock2
[Test]
public void UpdateComments()
{
const int arbitraryId = 1;
Comment comment = new Comment();
SqlParameter idParam = new SqlParameter("#ChangeId", arbitraryId);
Expect.Once.On(mockSqlDao).Method("ExecuteNonQuery")
.With("usp_Update_Comment", idParam);
changeDao.UpdateComment(arbitraryId, comment);
mocks.VerifyAllExpectationsHaveBeenMet();
}
I received this error:
NMock2.Internal.ExpectationException: unexpected invocation of sqlDao.ExecuteNonQuery("usp_Update_Comment", )
Expected:
1 time: sqlDao.ExecuteNonQuery(equal to "usp_Update_Comment", equal to <#ChangeId>) [called 0 times]
Questions:
How do you test with NMock2 when you
expected Parameter is SqlParameter?
How do you compare equality of two SqlParameters?
Because .Equals() is using the default implementation of Equals as far as I know (which means that a SqlParameter will only "equal" another SqlParameter if they are the same object), you will need to directly interrogate the properties of the parameter to ensure the correct data is being passed.
The Has.Property call within .With allows you to check the properties of a parameter without requiring that a parameter equals some other value. Try the following:
Expect.Once.On(mockSqlDao).Method("ExecuteNonQuery")
.With("usp_Update_Comment", Has.Property("ParameterName").EqualTo("#Id") &
Has.Property("Value").EqualTo(1));