Corrected some memory leaks at exit due to stringToArgcArgv().

This commit is contained in:
Claudio Maggioni 2016-05-01 16:32:41 +02:00
parent dd2e2ad50b
commit 40f2b2ee6b
6 changed files with 48 additions and 13 deletions

View file

@ -92,6 +92,8 @@ namespace mshconsole {
while (poptPeekArg(pc) != NULL)
nonOptionArgs.push_back(const_cast<const char*>(poptGetArg(pc)));
poptFreeContext(pc);
return (*funcCommand)(c,datas,nonOptionArgs);
}
@ -110,5 +112,10 @@ namespace mshconsole {
}
}
}
Command::~Command(){
}
const struct poptOption Command::POPT_TERMINATOR = {NULL,'\0',POPT_ARG_NONE,NULL,-1,NULL,NULL};
}

View file

@ -55,17 +55,21 @@ int main(int argc, char **argv)
string c = "msh-console-test";
string ps = "[msh-console-test]:";
Shell mshConsoleTest(c, ps, cin,cout,cerr, &setup);
Command* help = new Command("help", &helpExecute);
Command help("help", &helpExecute);
struct poptOption h = {"help",'h',POPT_ARG_NONE,NULL,1000,"advance","advaced options"};
struct poptOption p = {"prova",'p',POPT_ARG_STRING,NULL,1000,"cose","cosecose"};
help->addOption(h);
help->addOption(p);
help.addOption(h);
help.addOption(p);
Command exit("exit", &exitExecute);
Command cd("cd", &cdExecute);
//add builtin commands
mshConsoleTest.addCmd(help);
mshConsoleTest.addCmd(new Command("exit", &exitExecute));
mshConsoleTest.addCmd(new Command("cd", &cdExecute));
mshConsoleTest.addCmd(&help);
mshConsoleTest.addCmd(&cd);
mshConsoleTest.addCmd(&exit);
mshConsoleTest.launch();
return EXIT_SUCCESS;
}

View file

@ -60,11 +60,10 @@ namespace mshconsole {
//Run the shell loop.
int exitCode;
std::string* line=nullptr;
struct Params p;
try{
std::string* line=nullptr;
struct Params p;
while(1){
delete line;
outputStream << ps << " "; //Print the prompt.
@ -91,8 +90,13 @@ namespace mshconsole {
//Execute the command.
executeCmd(p);
//Free p
deleteParams(p);
};
} catch(CommandExecutor::ExitException c) {
delete line;
deleteParams(p);
exitCode=c.getCode();
}
@ -120,7 +124,9 @@ namespace mshconsole {
catch (CommandNotFoundException){}
//execute bash command or program
if((a=execvp(p.argv[0], p.argv)) == -1) {
a=execvp(p.argv[0], p.argv);
if(a == -1) {
outputStream << name << ": execution failed. Errno is set to: "<<strerror(errno)<<"\n";
std::exit(EXIT_FAILURE);
}
@ -181,9 +187,14 @@ namespace mshconsole {
struct sigaction* setHandler(unsigned signal, void (*funcptr)(int, siginfo_t*, void*)){
struct sigaction* before = new struct sigaction();
struct sigaction sa;
sigset_t mask;
sigemptyset(&mask);
sigaddset(&mask, SIGTERM);
sa.sa_mask=mask;
sa.sa_sigaction = funcptr;
sa.sa_flags = 0;
sa.sa_flags = SA_RESTART;
sigaction(signal, &sa, before);
return before;
}
void restoreHandler(unsigned signal, struct sigaction* before){
@ -212,6 +223,10 @@ namespace mshconsole {
return p;
}
void Shell::deleteParams(struct Params p){
freeString(p.argc,p.argv);
}
bool Shell::SIGINTRaised = false;
void Shell::addCmd(Command* cmd, bool isthread){

View file

@ -71,6 +71,7 @@ namespace mshconsole {
static void SIGINTHandler(int,siginfo_t *info, void *);
std::string* readLine();
struct Params splitLine(const std::string* line);
void deleteParams(struct Params p);
class IsUndoingLineException {};
class CommandNotFoundException {};

View file

@ -37,7 +37,7 @@ namespace StringToArgcArgv{
{
std::vector<std::string> args = parse(str);
*argv = (char**)std::malloc((args.size()+1) * sizeof(char*));
*argv = new char*[args.size()+1]();
int i=0;
for(std::vector<std::string>::iterator it = args.begin();
@ -45,7 +45,7 @@ namespace StringToArgcArgv{
++it, ++i)
{
std::string arg = *it;
(*argv)[i] = (char*)std::malloc((arg.length()+1) * sizeof(char));
(*argv)[i] = new char[arg.length()+1]();
std::strcpy((*argv)[i], arg.c_str());
}
(*argv)[i]=NULL;
@ -53,6 +53,13 @@ namespace StringToArgcArgv{
*argc = args.size();
}
void freeString(int& argc, char**& argv){
for(int i=0; i<argc; i++){
delete[] argv[i];
}
delete[] argv;
}
std::vector<std::string> parse(const std::string& args)
{
std::stringstream ain(args); // used to iterate over input string

View file

@ -42,5 +42,6 @@ namespace StringToArgcArgv{
bool _isWhitespace(char c);
std::vector<std::string> parse(const std::string& args);
void stringToArgcArgv(const std::string& str, int* argc, char*** argv);
void freeString(int& argc, char**& argv);
}
#endif //STRINGTOARGCARGV_H