I am a noobie with C++. My first learning project uses GoogleTest and GoolgleMock, but, of course, I am new to those also. I installed googletestmock.v.141 v101 via NuGet. My main app, AstronomyCalculations, builds and runs without a problem. My test app, GMock, throws three LNK2019 errors when I try to build it.
Severity Code Description Project File Line Suppression State
Error LNK2019 unresolved external symbol "public: __cdecl easter::easter(void)" (??0easter##QEAA#XZ) referenced in function "private: virtual void __cdecl GET_THE_DATE_OF_EASTER_ShouldReturnDateOfEaster_Test::TestBody(void)" (?TestBody#GET_THE_DATE_OF_EASTER_ShouldReturnDateOfEaster_Test##EEAAXXZ) GMock D:\Dev\Projects\AstronomyCalculations\GMock\GMock.obj 1
Severity Code Description Project File Line Suppression State
Error LNK2019 unresolved external symbol "public: __cdecl easter::~easter(void)" (??1easter##QEAA#XZ) referenced in function "private: virtual void __cdecl GET_THE_DATE_OF_EASTER_ShouldReturnDateOfEaster_Test::TestBody(void)" (?TestBody#GET_THE_DATE_OF_EASTER_ShouldReturnDateOfEaster_Test##EEAAXXZ) GMock D:\Dev\Projects\AstronomyCalculations\GMock\GMock.obj 1
Severity Code Description Project File Line Suppression State
Error LNK2019 unresolved external symbol "public: struct tm __cdecl easter::get_easter_date(int)const " (?get_easter_date#easter##QEBA?AUtm##H#Z) referenced in function "private: virtual void __cdecl GET_THE_DATE_OF_EASTER_ShouldReturnDateOfEaster_Test::TestBody(void)" (?TestBody#GET_THE_DATE_OF_EASTER_ShouldReturnDateOfEaster_Test##EEAAXXZ) GMock D:\Dev\Projects\AstronomyCalculations\GMock\GMock.obj 1
// AstronomyCalculations.cpp
int main() {
return 0;
}
// Easter.h
#pragma once
#include <ctime>
#include <string>
class easter
{
public:
easter();
~easter();
tm get_easter_date(int easter_year) const;
};
// Easter.cpp
#include "Easter.h"
easter::easter()
{
}
easter::~easter()
= default;
tm easter::get_easter_date(const int easter_year) const
{
const auto a = easter_year % 19;
const auto b = easter_year / 100;
const auto c = easter_year % 100;
const auto d = b / 4;
const auto e = b % 4;
const auto f = (b + 8) / 25;
const auto g = (b - f + 1) / 3;
const auto h = ((19 * a) + b - d - g + 15) % 30;
const auto i = c / 4;
const auto k = c % 4;
const auto l = (32 + (2 * e) + (2 * i) - h - k) % 7;
const auto m = (a + (11 * h) + (22 * l)) / 451;
const auto easter_month = (h + l - (7 * m) + 114) / 31;
const auto easter_day = ((h + l - (7 * m) + 114) % 31) + 1;
auto date_string = std::to_string(easter_year) +
"-" +
std::to_string(easter_month) +
"-" +
std::to_string(easter_day) +
" 00:00:00";
char date[20]; //a 1 char space for null is also required
strcpy_s(date, date_string.c_str());
tm ltm{};
char seps[] = " -:";
char *next_token = nullptr;
auto token = strtok_s(date, seps, &next_token);
ltm.tm_year = strtol(token, nullptr, 10);
token = strtok_s(nullptr, seps, &next_token);
ltm.tm_mon = strtol(token, nullptr, 10);
token = strtok_s(nullptr, seps, &next_token);
ltm.tm_mday = strtol(token, nullptr, 10);
token = strtok_s(nullptr, seps, &next_token);
ltm.tm_hour = strtol(token, nullptr, 10);
token = strtok_s(nullptr, seps, &next_token);
ltm.tm_min = strtol(token, nullptr, 10);
token = strtok_s(nullptr, seps, &next_token);
ltm.tm_sec = strtol(token, nullptr, 10);
ltm.tm_wday = 0;
return ltm;
}
// GMock.cpp
#include "stdafx.h"
#include "gmock/gmock.h"
#include "gtest/gtest.h"
#include "Easter.h"
int main(int argc, char** argv)
{
::testing::InitGoogleMock(&argc, argv);
return RUN_ALL_TESTS();
}
TEST(GET_THE_DATE_OF_EASTER, ShouldReturnDateOfEaster)
{
easter estr;
const auto result = estr.get_easter_date(2000);
ASSERT_EQ(result.tm_year, 2000);
}
The linker seems unable to find the functions easter::easter(void), easter::~easter(void), and easter::get_easter_date(int)const
You are obviously including easter.h (and have it in your search path, or the compiler would have complained) but are you actually compiling easter.cpp or a mock object of it? (As far as I can tell from your sourcecode you are not actually mocking the class either). The header file is enough to satisfy the compiler, but when the linker tries to put the application together and realizes it is missing the object file, it balks - throwing LNK2019.
I can only strongly reccommend you look deeper into the documentation available for gtest & gmock.
In addition, you may also reconsider your naming schemes - Class types usually begin with an uppercase (i.e. Easter, not easter) to better tell them from variable names (which begin with lowercase). Also don't call your variables a, b, c, d - const auto a and its ilk are horrible to read, debug, and you will curse yourself I you ever find yourself in the postion of having to revisit the code after some weeks. Even if this were only some practice project, please also practice using good coding standards & naming conventions, so you (automatically) use them on bigger projects.
I finally solved this when I discovered that GoogleTest can be added in Visual Studio 2017 as a new project. Of course, I had to remove my original test project first and then add the new test project. It all worked out in the end, but, of course, I have no idea of why the link errors showed up in my original testing project; other than CharonX's insights.
Related
I am trying to learn gecode and am trying to get the example found here to work.
// To use integer variables and constraints
#include <gecode/int.hh>
// To make modeling more comfortable
#include <gecode/minimodel.hh> // To use search engines
#include <gecode/search.hh>
// To avoid typing Gecode:: all the time
using namespace Gecode;
class SendMoreMoney : public Space {
protected:
IntVarArray x;
public:
SendMoreMoney() : x(*this, 8, 0, 9) {
IntVar s(x[0]), e(x[1]), n(x[2]), d(x[3]), m(x[4]), o(x[5]), r(x[6]),
y(x[7]);
rel(*this, s != 0);
rel(*this, m != 0);
distinct(*this, x);
rel(*this,
1000 * s + 100 * e + 10 * n + d + 1000 * m + 100 * o + 10 * r + e ==
10000 * m + 1000 * o + 100 * n + 10 * e + y);
branch(*this, x, INT_VAR_SIZE_MIN(), INT_VAL_MIN());
}
SendMoreMoney(SendMoreMoney& s) : Space(s) { x.update(*this, s.x); }
virtual Space* copy() { return new SendMoreMoney(*this); }
void print() const { std::cout << x << std::endl; }
};
int main() {
SendMoreMoney* m = new SendMoreMoney;
DFS<SendMoreMoney> e(m);
delete m;
while (SendMoreMoney s = e.next()) {
s->print();
delete s;
}
}
I end up with the following compilation errors.
error: no matching function for call to 'Gecode::IntVarArray::update(SendMoreMoney&, Gecode::IntVarArray&)'
27 | x.update(*this, s.x);
| ^
and
error: invalid new-expression of abstract class type 'SendMoreMoney'
30 | return new SendMoreMoney(*this);
|
I do not understand where these come from. IntVarArray certainly has an update function whose first argument is a Space object and SendMoreMoney inherits from Space so what is the problem? This code is verbatim from the example I found so presumably it should work as-is.
e.next() returns a pointer of the cloned space (SendMoreMoney). You must use while (SendMoreMoney* s = e.next())
I am looking to use the C++ neural network library "OpenNN".
http://www.opennn.net/
I am relatively new to C++ project management and I believe my issue is caused by this.
I have cloned the openNN repo.
I copied the relevant folders form the repo across in to the folder that i created to contain all OpenNN project i plan to make.
I then made a c++ console application in visual studio, in this folder that i am using for testing.
so dir structure is :
OpenNN (where i plan to keep all openNN projects)
---eigen
---opennn
---tinyxml2
---OpenNNTest (my test project folder)
I have done some testing with the Vector and Matrix classes that are part of OpenNN and that all worked fine.
The below code however returns the following two external symbol errors:
Error LNK2019 unresolved external symbol "public: __thiscall OpenNN::NeuralNetwork::NeuralNetwork(class OpenNN::Vector<unsigned int> const &)" (??0NeuralNetwork#OpenNN##QAE#ABV?$Vector#I#1##Z) referenced in function "void __cdecl NNTest(void)" (?NNTest##YAXXZ) OpenNNTest D:\Projects\OpenNN\OpenNNTest\OpenNNTest\OpenNNTest.obj 1
Error LNK2019 unresolved external symbol "public: virtual __thiscall
OpenNN::NeuralNetwork::~NeuralNetwork(void)" (??1NeuralNetwork#OpenNN##UAE#XZ) referenced in function "void __cdecl NNTest(void)" (?NNTest##YAXXZ) OpenNNTest D:\Projects\OpenNN\OpenNNTest\OpenNNTest\OpenNNTest.obj 1
interestingly, if I change:
OpenNN::NeuralNetwork nn(architecture);
to
OpenNN::NeuralNetwork nn();
No issues, as if it finds the default constructor but not the overloaded one?
The code I am using is as follows:
#include "stdafx.h"
#include "../../opennn/opennn.h"
using namespace OpenNN;
using std::cout;
using std::endl;
void NNTest()
{
OpenNN::Vector<unsigned> architecture(5);
architecture[0] = 2;
architecture[1] = 2;
architecture[2] = 4;
architecture[3] = 3;
architecture[4] = 1;
OpenNN::NeuralNetwork nn(architecture);
//Vector<double> inputs(2);
//inputs[0] = 0.5;
//inputs[1] = 0.1;
//Vector<double> outputs = nn.calculate_outputs(inputs);
//cout << outputs << endl;
//nn.save("neural_network.xml");
}
int main()
{
NNTest();
getchar();
return 0;
}
You need to change the type unsigned to size_t:
OpenNN::Vector<size_t> architecture(5);
architecture[0] = 2;
architecture[1] = 2;
architecture[2] = 4;
architecture[3] = 3;
architecture[4] = 1;
OpenNN::NeuralNetwork nn(architecture);
I hope that helps.
Those #things are EmPy
C++
const char *
publish__#(spec.base_type.type)(void * untyped_data_writer, const void * untyped_message)
{
DataWriter * topic_writer = static_cast<DataWriter *>(untyped_data_writer);
const __ros_msg_type & ros_message = *(const __ros_msg_type *)untyped_message;
__dds_msg_type dds_message;
conversion_cpp(ros_message, dds_message);
#(__dds_msg_type_prefix)DataWriter * data_writer =
#(__dds_msg_type_prefix)DataWriter::_narrow(topic_writer);
DDS::ReturnCode_t status = data_writer->write(dds_message, DDS::HANDLE_NIL);
// some common switch statements in C and C++
}
}
C
static const char *
publish(void * data_writer, const void * cool_message)
{
if (!data_writer) {return "data writer handle is null";}
if (!cool_message) {return "ros message handle is null";}
DDS::DataWriter * topic_writer = static_cast<DDS::DataWriter *>(data_writer);
__dds_msg_type dds_message;
const char * err_msg = conversion_c(cool_message, &dds_message);
if (err_msg != 0) {return err_msg;}
#(__dds_msg_type_prefix)DataWriter * data_writer =
#(__dds_msg_type_prefix)DataWriter::_narrow(topic_writer);
DDS::ReturnCode_t status = data_writer->write(dds_message, DDS::HANDLE_NIL);
#[for field in spec.fields]#
#[if field.type.type == 'string']#
#[if field.type.is_array]#
{
#[if field.type.array_size]#
size_t size = #(field.type.array_size);
#[else]#
size_t size = dds_message.#(field.name)_.length();
#[end if]#
for (DDS::ULong i = 0; i < size; ++i) {
// This causes the DDS::String_mgr to release the given c string without freeing it.
dds_message.#(field.name)_[i]._retn();
}
}
#[else]#
// This causes the DDS::String_mgr to release the given c string without freeing it.
dds_message.#(field.name)_._retn();
#[end if]#
#[end if]#
#[end for]#
// some common switch statements in C and C++
}
}
This question is a bit specific to an open source project I am trying to contribute to, so I ll point to the exact functions I guess.
This is the original C method
and this is the C++ method
Do I need to use function pointers?
Another thing going on here is that the C package depends on the C++ package.
(Maybe this isn't good question or is a vague question, but I am not sure what to do as I am new to this codebase)
This question already has answers here:
What is an undefined reference/unresolved external symbol error and how do I fix it?
(39 answers)
Closed 7 years ago.
I have read the model answer on unresolved externals and found it to be incredibly useful and have got it down to just these last two stubborn errors which are beyond me.
I've attached all the code just in case, if you would like to see the headers or anything else please say.
// Stokes theory calculations
#include <math.h>
#include <stdio.h>
#include <process.h>
#include <string.h>
#include <conio.h>
#include <stdlib.h>
#define ANSI
#include "../Allocation.h"
#define Main
#define Char char
#define Int int
#define Double double
#include "../Allocation.h"
#include "../Headers.h"
Double
kH, skd, ckd, tkd, SU;
Double
ss[6], t[6], C[6], D[6], E[6], e[6];
// Main program
int main(void)
{
int i, Read_data(void), iter, Iter_limit = 40;
double F(double), kd1, kd2, kFM, omega, delta, accuracy = 1.e-6, F1, F2, Fd;
void CDE(double), AB(void), Output(void);
Input1 = fopen("../Data.dat", "r");
strcpy(Convergence_file, "../Convergence.dat");
strcpy(Points_file, "../Points.dat");
monitor = stdout;
strcpy(Theory, "Stokes");
strcpy(Diagname, "../Catalogue.res");
Read_data();
z = dvector(0, 2 * n + 10);
Y = dvector(0, n);
B = dvector(0, n);
coeff = dvector(0, n);
Tanh = dvector(0, n);
monitor = stdout;
H = MaxH;
iff(Case, Wavelength)
{
kd = 2. * pi / L;
kH = kd * H;
CDE(kd);
}
// If period is specified, solve dispersion relation using secant method
// Until February 2015 the bisection method was used for this.
// I found that in an extreme case (large current) the bracketting
// of the solution was not correct, and the program failed,
// without printing out a proper error message.
iff(Case, Period)
{
fprintf(monitor, "\n# Period has been specified.\n# Now solving for L/d iteratively, printing to check convergence\n\n");
omega = 2 * pi / T;
// Fenton & McKee for initial estimate
kFM = omega*omega*pow(1 / tanh(pow(omega, 1.5)), (2. / 3.));
kd1 = kFM;
kd2 = kFM*1.01;
CDE(kd2);
F2 = F(kd2);
for (iter = 1; iter <= Iter_limit; ++iter)
{
CDE(kd1);
F1 = F(kd1);
Fd = (F2 - F1) / (kd2 - kd1);
delta = F1 / Fd;
kd2 = kd1;
kd1 = kd1 - delta;
fprintf(monitor, "%8.4f\n", 2 * pi / kd1);
if (fabs(delta / kd1) < accuracy) break;
F2 = F1;
if (iter >= Iter_limit)
{
printf("\n\nSecant for solution of wavenumber has not converged");
printf("\nContact John Fenton johndfenton#gmail.com");
getch();
exit(1);
}
}
kd = kd1;
kH = kd * H;
}
z[1] = kd;
z[2] = kH;
SU = 0.5*kH / pow(kd, 3);
printf("\n# Stokes-Ursell no.: %7.3f", SU);
if (SU > 0.5)
printf(" > 1/2. Results are unreliable");
else
printf(" < 1/2, Stokes theory should be valid");
e[1] = 0.5 * kH;
for (i = 2; i <= n; i++) e[i] = e[i - 1] * e[1];
// Calculate coefficients
AB();
z[7] = C[0] + e[2] * C[2] + e[4] * C[4]; // ubar
z[8] = -e[2] * D[2] - e[4] * D[4];
z[9] = 0.5 * C[0] * C[0] + e[2] * E[2] + e[4] * E[4];
if (Current_criterion == 1)
{
z[5] = Current*sqrt(kd);
z[4] = z[7] + z[5];
z[6] = z[4] + z[8] / kd - z[7];
}
if (Current_criterion == 2)
{
z[6] = Current*sqrt(kd);
z[4] = z[6] - z[8] / kd + z[7];
z[5] = z[4] - z[7];
}
iff(Case, Wavelength) z[3] = 2 * pi / z[4];
iff(Case, Period) z[3] = T * sqrt(kd);
for (i = 1; i <= n; i++)
Tanh[i] = tanh(i*z[1]);
// Output results and picture of wave
Solution = fopen("Solution.res", "w");
Elevation = fopen("Surface.res", "w");
Flowfield = fopen("Flowfield.res", "w");
Output();
fflush(NULL);
printf("\nTouch key to continue "); getch();
printf("\n\nFinished\n");
}
I get these error messages:
LNK2019 unresolved external symbol "void __cdecl Output(void)" (?Output##YAXXZ) referenced in function _main Stokes
LNK2019 unresolved external symbol "double * __cdecl dvector(long,long)" (?dvector##YAPANJJ#Z) referenced in function _main Stokes
I have checked everything on the list given to try and find where these errors are coming from and have whittled it down to just these two left.
Things tried so far:
Checking basic syntax
Checking and ensuring correct headers are available
Looked at external dependencies (but i don't really know what i'm doing here)
Looked at the solutions tried here but none worked.
Any help would be greatly appreciated!
Unresolved External Symbols means that your code can't find the definition of the method or class you're trying to use. This usually means one (or more) of several things has happened:
You didn't point to the directory that contains the object library (.lib on Windows, .so on Linux) for the library you're using
You forgot to specify in the linker that you need to use the library in question (that list of kernel32.lib, user32.lib,... needs to include the name of the library you're using)
The library you're trying to use is meant to be linked statically and you're trying to link it dynamically (or vise-versa). Check the documentation for the library and make sure you're using the correct form. Some libraries expect extra #define statements to be included or omitted depending on whether you're linking statically or dynamically.
You changed build options and forgot to update the libraries in the other build options. If you're set to Release or x64, check to make sure that your build options are set correctly in all environments.
EDIT: I'll also corroborate what the others said in the original comment thread: make sure that the code that defines Output() and dvector() are being linked to by your code.
There's a few other options, but those are the big ones that happen most frequently.
I want to create a managed C++ unit test project to test an unmanaged MFC project. I have read msujaws's procedural and followed it. I implemented a test method to test the return string of a function like so:
#include "stdafx.h"
#include "TxStats.h"
#include <cstdlib>
#include <atlstr.h>
#pragma managed
#using <mscorlib.dll>
#using <System.dll>
#using <system.data.dll>
using namespace std;
using namespace System;
using namespace System::Text;
using namespace System::Text::RegularExpressions;
using namespace System::Collections::Generic;
using namespace System::Runtime::InteropServices;
using namespace Microsoft::VisualStudio::TestTools::UnitTesting;
namespace AUnitTest
{
[TestClass]
public ref class TxStatsTest
{
private:
TestContext^ testContextInstance;
public:
/// <summary>
///Gets or sets the test context which provides
///information about and functionality for the current test run.
///</summary>
property Microsoft::VisualStudio::TestTools::UnitTesting::TestContext^ TestContext
{
Microsoft::VisualStudio::TestTools::UnitTesting::TestContext^ get()
{
return testContextInstance;
}
System::Void set(Microsoft::VisualStudio::TestTools::UnitTesting::TestContext^ value)
{
testContextInstance = value;
}
};
#pragma region Additional test attributes
//
//You can use the following additional attributes as you write your tests:
//
//Use ClassInitialize to run code before running the first test in the class
//[ClassInitialize()]
//static void MyClassInitialize(TestContext^ testContext) {};
//
//Use ClassCleanup to run code after all tests in a class have run
//[ClassCleanup()]
//static void MyClassCleanup() {};
//
//Use TestInitialize to run code before running each test
//[TestInitialize()]
//void MyTestInitialize() {};
//
//Use TestCleanup to run code after each test has run
//[TestCleanup()]
//void MyTestCleanup() {};
//
#pragma endregion
[TestMethod]
void TestGetTxRateStr()
{
/* str to CString
CManagedClass* pCManagedClass = new CManagedClass();
pCManagedClass->ShowMessage(strMessage);
char* szMessage = (char*)Marshal::StringToHGlobalAnsi(strMessage);
CUnmanagedClass cUnmanagedClass; cUnmanagedClass.ShowMessageBox(szMessage);
Marshal::FreeHGlobal((int)szMessage);
*/
CString out = TxStats::GetTxRateStr(1024);
// convert between MFC and .NET String implementations
String ^ myManagedString = Marshal::PtrToStringAnsi((IntPtr) (char *) out.GetBuffer());
String ^ ret = myManagedString ;///gcnew String( );
Regex ^ matStr = gcnew Regex("1024 KB/s");
StringAssert::Matches(ret, matStr);
}
};
}
That tests the code in a DIFFERENT project that looks like this:
#include "stdafx.h"
#include "TxStats.h"
TxStats::TxStats()
{
}
/*
This method returns a data rate string formatted in either Bytes, KBytes, MBytes or GBytes per sec
from an int of the bytes per second.
*/
CString TxStats::GetTxRateStr(__int64 Bps)
{
enum DataUnits dunit;
const __int64 dataSizes[]= { 0x1, // 2 ^ 0
0x400, // 2 ^ 10
0x100000, // 2 ^ 20
0x40000000};// 2 ^ 30
const char *dataStrs[] = { "B/s",
"KB/s",
"MB/s",
"GB/s"};
CString out;
double datarate;
bool finish = false;
for ( dunit = A_KBYTE; dunit <= LARGER_THAN_BIGGEST_UNIT; dunit = DataUnits(dunit+1) )
{
if ( dunit == LARGER_THAN_BIGGEST_UNIT )
{
if (dataSizes[dunit - 1] <= Bps )
{
//Gigabytes / sec
datarate = Bps / ((double) dataSizes[dunit - 1]);
out.Format("%4.2f %s", datarate, dataStrs[dunit - 1]);
finish = true;
break;
}
}
else
{
if (Bps < dataSizes[dunit])
{
//(Kilo, Mega)bytes / sec
datarate = Bps / ((double) dataSizes[dunit - 1]);
out.Format("%4.2f %s", datarate, dataStrs[dunit - 1]);
finish = true;
break;
}
}
}
if (! finish)
{
out.Format("%s", "Unknown!");
}
return out.GetBuffer();
}
void TxStats::BytesToSizeStr(__int64 bytes, CString &out)
{
if (bytes < 0)
{
out = "Err";
}
else if (bytes == 0)
{
out = "0B";
}
else
{
CString size;
CString byteChar = "B";
CString unit;
int val;
if (bytes < 1024)
{
//Bytes
unit = "";
val = (int)bytes;
}
else if ( (bytes >> 10) < 1024 )
{
//Kilobytes
unit = "K";
__int64 div = 1 << 10;
val = (int) (bytes / ((double) div ));
}
else if ( (bytes >> 20) < 1024 )
{
//Megabytes
unit = "M";
__int64 div = 1 << 20;
val = (int) (bytes / ((double) div ));
}
else
{
//Else assume gigabytes
unit = "G";
__int64 div = 1 << 30;
val = (int) (bytes / ((double) div ));
}
unit = unit + byteChar;
const char * unitCharBuf = unit.GetBuffer();
size.Format("%d%s", ((int) val), unitCharBuf);
out = size.GetBuffer();
}
}
However, when I compile this code I get the following error:
2>TxStatsTest.obj : error LNK2028: unresolved token (0A0005D4) "public: static class ATL::CStringT<char,class StrTraitMFC_DLL<char,class ATL::ChTraitsCRT<char> > > __cdecl TxStats::GetTxRateStr(__int64)" (?GetTxRateStr#TxStats##$$FSA?AV?$CStringT#DV?$StrTraitMFC_DLL#DV?$ChTraitsCRT#D#ATL#####ATL##_J#Z) referenced in function "public: void __clrcall AUnitTest::TxStatsTest::TestGetTxRateStr(void)" (?TestGetTxRateStr#TxStatsTest#AUnitTest##$$FQ$AAMXXZ)
2>TxStatsTest.obj : error LNK2019: unresolved external symbol "public: static class ATL::CStringT<char,class StrTraitMFC_DLL<char,class ATL::ChTraitsCRT<char> > > __cdecl TxStats::GetTxRateStr(__int64)" (?GetTxRateStr#TxStats##$$FSA?AV?$CStringT#DV?$StrTraitMFC_DLL#DV?$ChTraitsCRT#D#ATL#####ATL##_J#Z) referenced in function "public: void __clrcall AUnitTest::TxStatsTest::TestGetTxRateStr(void)" (?TestGetTxRateStr#TxStatsTest#AUnitTest##$$FQ$AAMXXZ)
2>\trunk\<proj>\Debug\AUnitTest.dll : fatal error LNK1120: 2 unresolved externals
2>Caching metadata information for c:\program files\microsoft visual studio 9.0\common7\ide\publicassemblies\microsoft.visualstudio.qualitytools.unittestframework.dll...
2>Build log was saved at "file://trunk\<proj>\AUnitTest\Debug\BuildLog.htm"
2>AUnitTest - 3 error(s), 0 warning(s)
========== Rebuild All: 1 succeeded, 1 failed, 0 skipped ==========
Can anyone suggest why the Unit test project might not be linking against the obj files of the main project? (I have already specified the main project as a dependency of the unit test project)
You can add
#pragma comment(lib, "TxStats.lib")
to your unit test project's stdafx.cpp to link against the other library.
You need to add the *.obj files of the project you want to test to the linker inputs of the unit test project