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

Debug Framework changes for dump routines and custom assert #300

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

Conversation

anilsadineni
Copy link

These changes along with changes in sonic-utilities are needed to test the framework

The code is inline with design from:
sonic-net/SONiC#398

These changes along with changes in sonic-utilities are needed to test
the framework
The code is inline with design from:
sonic-net/SONiC#398
UNSPECIFIED
};
static void setAssertAction(std::string val);
static void custom_assert(bool exp, AssertAction act, const char *func, const unsigned line);
Copy link
Contributor

@qiluo-msft qiluo-msft Sep 25, 2019

Choose a reason for hiding this comment

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

custom_assert [](start = 16, length = 13)

customAssert #Closed

Copy link
Author

Choose a reason for hiding this comment

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

done


#ifdef assert
#undef assert
#define assert(exp) Debugframework::custom_assert(exp, Debugframework::AssertAction::UNSPECIFIED, __PRETTY_FUNCTION__, __LINE__)
Copy link
Contributor

Choose a reason for hiding this comment

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

assert [](start = 8, length = 6)

Why re-define standard assert macro? Originally assert will only take effect when build in DEBUG mode, and totally optimized in RELEASE mode. Your use case is different. You may choose another name.

Copy link
Author

Choose a reason for hiding this comment

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

The basic idea here is that without having to change the code where assert has been used, bring customAssert and have this enabled even in production builds. Based on the configuration either log or collect more info or abort shall be action when assert condition is met and hence standard assert is re-defined.

Copy link
Contributor

Choose a reason for hiding this comment

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

I am worried about the side-effect. Assume there is a third party header file, which uses assert intensively for DEBUG build. If someone include this header before third party one, then there will be overhead to RELEASE build.


In reply to: 328907805 [](ancestors = 328907805)

Copy link
Author

Choose a reason for hiding this comment

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

I am not sure of the overhead to release build you mention. What would otherwise have no effect in release build will now have some outcome when assert condition is hit. Is that what you refer?

The outcome of assert is now controlled using a default or configuration command. The idea is to not miss out on assert but have some insight into it and the level of overhead is controlled. So I am not sure if we can term that overhead or side-effect, this is by design the desired effect for better debug ability.


typedef void (*DumpInfoFunc)(std::string, KeyOpFieldsValuesTuple);

class Debugframework
Copy link
Contributor

@qiluo-msft qiluo-msft Sep 25, 2019

Choose a reason for hiding this comment

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

Debugframework [](start = 6, length = 14)

DebugFramework #Closed

Copy link
Author

Choose a reason for hiding this comment

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

changed this in lot of places..

}

Debugframework::Debugframework() {
// Read .ini configuration file to init
Copy link
Contributor

@qiluo-msft qiluo-msft Sep 25, 2019

Choose a reason for hiding this comment

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

Read .ini configuration file to init [](start = 7, length = 36)

Is the comment related to code? #Closed

Copy link
Author

Choose a reason for hiding this comment

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

It is now deadcode. The original plan was to have a init config file but since this is library and not daemon it did not make lot of sense to have a config file. Shall remove.


Debugframework::~Debugframework() {
//m_registeredComps.clear();
//m_configParams.clear();
Copy link
Contributor

@qiluo-msft qiluo-msft Sep 25, 2019

Choose a reason for hiding this comment

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

remove dead code #Closed

Copy link
Author

Choose a reason for hiding this comment

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

done

//m_configParams.clear();
}

void Debugframework::linkWithFrameworkNoThread(std::string &componentName)
Copy link
Contributor

@qiluo-msft qiluo-msft Sep 25, 2019

Choose a reason for hiding this comment

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

std::string & [](start = 47, length = 13)

const std::string & or std::string
Many more below. #Closed

Copy link
Author

Choose a reason for hiding this comment

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

done

std::thread t(Debugframework::runnableThread, componentName, funcPtr);
t.detach();

}
Copy link
Contributor

@qiluo-msft qiluo-msft Sep 26, 2019

Choose a reason for hiding this comment

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

remove extra empty line #Closed

Copy link
Author

Choose a reason for hiding this comment

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

done

@@ -44,6 +44,11 @@ namespace swss {
#define APP_SFLOW_TABLE_NAME "SFLOW_TABLE"
#define APP_SFLOW_SESSION_TABLE_NAME "SFLOW_SESSION_TABLE"
#define APP_SFLOW_SAMPLE_RATE_TABLE_NAME "SFLOW_SAMPLE_RATE_TABLE"
#define APP_DEBUGFM_CONFIG_TABLE_NAME "DEBUGFM_CONFIG_TABLE"
Copy link
Contributor

@qiluo-msft qiluo-msft Sep 26, 2019

Choose a reason for hiding this comment

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

APP [](start = 8, length = 3)

Maybe the tables should be moved to ConfigDB. #Closed

Copy link
Author

Choose a reason for hiding this comment

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

This was discussed in the design review meeting. This is really only on a trigger and hence considered to place it in the APP_DB.


typedef void (*DumpInfoFunc)(std::string, KeyOpFieldsValuesTuple);

class Debugframework
Copy link
Contributor

@qiluo-msft qiluo-msft Sep 26, 2019

Choose a reason for hiding this comment

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

[](start = 20, length = 1)

an extra trailing blank #Closed

Copy link
Author

Choose a reason for hiding this comment

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

done

class Debugframework
{
public:
static Debugframework &getInstance(); /* To have only one instance aka singleton */
Copy link
Contributor

Choose a reason for hiding this comment

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

[](start = 26, length = 1)

an extra blank

Copy link
Author

Choose a reason for hiding this comment

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

done

static Debugframework &getInstance(); /* To have only one instance aka singleton */

//typedef std::function< void (std::string componentName, KeyOpFieldsValuesTuple args)> DumpInfoFunc;

Copy link
Contributor

@qiluo-msft qiluo-msft Sep 26, 2019

Choose a reason for hiding this comment

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

remove dead code #Closed

Copy link
Author

Choose a reason for hiding this comment

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

done

#include "notificationconsumer.h"
#include "notificationproducer.h"

#define ACTIONS_CONFIG_FILE "/etc/sonic/dbgFm.ini"
Copy link
Contributor

@qiluo-msft qiluo-msft Sep 26, 2019

Choose a reason for hiding this comment

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

ACTIONS_CONFIG_FILE [](start = 8, length = 19)

How is the macro used? #Closed

Copy link
Author

Choose a reason for hiding this comment

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

Same as above. With library doesnt make lot of sense. Shall remove this deadcode.

try{
(*funcPtr)(componentName, entry);
}catch(...){
throw "Registered dump routine returned error";
Copy link
Contributor

@qiluo-msft qiluo-msft Sep 26, 2019

Choose a reason for hiding this comment

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

returned error [](start = 54, length = 14)

threw an exception #Closed

Copy link
Author

Choose a reason for hiding this comment

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

This is already in the context of debug routines and additional exception handling is an overhead and hence not changing this for now.

}

/* Inform done with same key */
FieldValueTuple fvResp("RESPONSE", "SUCCESS");
Copy link
Contributor

@qiluo-msft qiluo-msft Sep 26, 2019

Choose a reason for hiding this comment

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

SUCCESS [](start = 55, length = 7)

When exception thrown, still SUCCESS? #Closed

Copy link
Author

Choose a reason for hiding this comment

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

Oops! response failure in the catch is missed. Shall correct it

Copy link
Contributor

@qiluo-msft qiluo-msft Nov 6, 2019

Choose a reason for hiding this comment

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

Sorry, I gave the wrong comment. In your second commit, any code after throw will not run, so it is dead code. Original code should be good. #Closed

{
// open a file in append mode and keep it open
std::fstream *outfile;
std::string options("/var/log/" + component + "_debug.log");
Copy link
Contributor

Choose a reason for hiding this comment

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

/var/log/ [](start = 29, length = 9)

Don't use fixed path, you should have a configuration for it.

Copy link
Author

Choose a reason for hiding this comment

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

The post scripts are TBD and for now there is nothing in configDB. When the post scripts (TBD) are in place this needs to allign with those scripts. Shall defer this till that point.

}
else
{
char buffer[0x1000];
Copy link
Contributor

@qiluo-msft qiluo-msft Sep 26, 2019

Choose a reason for hiding this comment

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

0x1000 [](start = 20, length = 6)

Better to allocate on heap #Closed

Copy link
Author

Choose a reason for hiding this comment

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

This is short lived and called several times and trying to get from heap might be really costly.

if (itr != dbgfm.m_compFds.end())
{
f = itr->second;
*f << buffer << "\n";
Copy link
Contributor

@qiluo-msft qiluo-msft Sep 26, 2019

Choose a reason for hiding this comment

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

"\n" [](start = 28, length = 4)

If you need flush, use endl #Closed

Copy link
Author

Choose a reason for hiding this comment

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

done

std::string comp("all");
std::string args("DETAIL:FULL;");
invokeTrigger(comp, args);
}
Copy link
Contributor

@qiluo-msft qiluo-msft Sep 26, 2019

Choose a reason for hiding this comment

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

break ? #Closed

Copy link
Author

Choose a reason for hiding this comment

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

As you see comment in line 427 break is not added intentionally, dump is exhaustive info and that should include backtrace as well

Copy link
Contributor

@qiluo-msft qiluo-msft left a comment

Choose a reason for hiding this comment

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

As comments.
The c++ source files should be well formatted like all existing files.


void Debugframework::linkWithFramework(std::string &componentName, const DumpInfoFunc funcPtr)
{
if (funcPtr == NULL)
Copy link
Contributor

@kcudnik kcudnik Sep 30, 2019

Choose a reason for hiding this comment

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

missing SWSS_LOG_ENTER() in many functions

Copy link
Author

Choose a reason for hiding this comment

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

Added for all relevant functions except in small utility functions that get called repeatedly

std::fstream *outfile;
std::string options("/var/log/" + component + "_debug.log");
try{
outfile = new std::fstream();
Copy link
Contributor

Choose a reason for hiding this comment

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

why this is a pointer ? not actual object? on s tack ?

Copy link
Author

Choose a reason for hiding this comment

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

This is created during begin and kept open while the components dumps info using multiple writes and in the end this is closed and freed.

#ifndef NO_RET_TYPE
#define NO_RET_TYPE [[noreturn]]
#endif
NO_RET_TYPE static void runnableThread(std::string componentName, const DumpInfoFunc funcPtr);
Copy link
Contributor

@kcudnik kcudnik Sep 30, 2019

Choose a reason for hiding this comment

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

if this is thread function, threads should be able to quit loop in nice way, for example in dtr there should be join thread and break run flag in thread so norturn flag would not be needed

Copy link
Author

Choose a reason for hiding this comment

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

This comes into picture if the component registers with a thread option and the thread stays until the component exits so this really never returns and hence the noreturn flag.

Debugframework &operator=(const Debugframework&);

static void listenDoneEvents(std::string componentName);
static void relayTrigger(std::string &componentName, KeyOpFieldsValuesTuple args);
Copy link
Contributor

Choose a reason for hiding this comment

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

all paramters in functions should be defined 1 per line and with prefixes In _Inout or Out

Copy link
Author

Choose a reason for hiding this comment

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

I am new to project and tried to stay consistent with other files in the dir.

bhaveshdell
bhaveshdell previously approved these changes Oct 18, 2019
(*funcPtr)(componentName, entry);
}catch(...){
throw "Registered dump routine returned error";
fvResp.second = "FAILURE";
Copy link
Contributor

Choose a reason for hiding this comment

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

will be never executed,
also please log error message if catch was catched

Copy link
Author

Choose a reason for hiding this comment

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

done

return;
}

void DebugFramework::dumpWrite(const std::string &component, const char *fmt, ...)
Copy link
Contributor

Choose a reason for hiding this comment

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

one param per line, also add In /Out etc prefixes

Copy link
Author

Choose a reason for hiding this comment

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

Are you referring to SAL annotation style of doxygen style? As mentioned in response to your earlier comment, I tried to stay consistent with the other files in the directory and elsewhere in the project. Can you please point me to any other file which followed your suggestion for me to be clear. Thanks,

{
std::fstream *out = itr->second;
out->close();
delete out;
Copy link
Contributor

Choose a reason for hiding this comment

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

use shared pointers in map/set, to not explicitly delete them

Copy link
Author

Choose a reason for hiding this comment

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

Good suggestion and optimization. However for now there are no components using this framework. Once the usage picks up, we need to revisit the file naming conventions, post scripts, uploads and based on that these changes might be moot. For now this is not in usual operations and only during debug and hence this might not be a lot of overhead even without the suggested optimization.

}

DebugFramework::PostAction DebugFramework::getPostAction()
{
Copy link
Contributor

Choose a reason for hiding this comment

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

missing SWSS_LOG_ENTER(); on every function

Copy link
Author

Choose a reason for hiding this comment

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

I have added to all the functions which does meaningful work other than helper functions and utility functions which will be called multiple times. Please check my comment above when I changed to address your review comments

case BTRACE:
{
std::FILE *fp = fopen(ASSERT_FILE, "w");
#define SIZE 100
Copy link
Contributor

Choose a reason for hiding this comment

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

please define at the file beginning and add more meaningfull name

Copy link
Author

Choose a reason for hiding this comment

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

done

table.set(component, fieldValues);
}

NO_RET_TYPE void DebugFramework::runnableThread(const std::string componentName, const DumpInfoFunc funcPtr)
Copy link
Contributor

@qiluo-msft qiluo-msft Nov 6, 2019

Choose a reason for hiding this comment

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

const std::string [](start = 48, length = 17)

const std::string & #Closed

Copy link
Author

Choose a reason for hiding this comment

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

done

} // end while loop
}

void DebugFramework::invokeTrigger(const std::string componentName, std::string argList)
Copy link
Contributor

@qiluo-msft qiluo-msft Nov 6, 2019

Choose a reason for hiding this comment

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

const std::string [](start = 35, length = 17)

const std::string & #Closed

Copy link
Author

Choose a reason for hiding this comment

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

done

t.detach();
}

void DebugFramework::listenDoneEvents(const std::string componentName)
Copy link
Contributor

@qiluo-msft qiluo-msft Nov 6, 2019

Choose a reason for hiding this comment

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

const std::string [](start = 38, length = 17)

const std::string & #Closed

Copy link
Author

Choose a reason for hiding this comment

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

done

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.

4 participants