Performance optimizations
- Replaced some exec() calls with functions - Removed resolved code being resolved again - Removed empty string subargs inserted upon parsing
This commit is contained in:
parent
5a7c2e0bf0
commit
a0155991e3
10 changed files with 157 additions and 89 deletions
|
|
@ -7,13 +7,14 @@
|
||||||
|
|
||||||
// boolean value of fct: if true, recurse on this object, if false, skip this object
|
// boolean value of fct: if true, recurse on this object, if false, skip this object
|
||||||
template<class... Args>
|
template<class... Args>
|
||||||
void recurse(void (&fct)(_obj*, Args...), _obj* o, Args... args)
|
void recurse(bool (&fct)(_obj*, Args...), _obj* o, Args... args)
|
||||||
{
|
{
|
||||||
if(o == nullptr)
|
if(o == nullptr)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
// execution
|
// execution
|
||||||
fct(o, args...);
|
if(!fct(o, args...))
|
||||||
|
return; // skip recurse if false
|
||||||
|
|
||||||
// recursive calls
|
// recursive calls
|
||||||
switch(o->type)
|
switch(o->type)
|
||||||
|
|
|
||||||
|
|
@ -3,6 +3,11 @@
|
||||||
|
|
||||||
#include "struc.hpp"
|
#include "struc.hpp"
|
||||||
|
|
||||||
|
extern std::vector<std::string> included;
|
||||||
|
|
||||||
|
bool add_include(std::string const& file);
|
||||||
|
|
||||||
|
void resolve(_obj* sh, shmain* parent);
|
||||||
void resolve(shmain* sh);
|
void resolve(shmain* sh);
|
||||||
|
|
||||||
#endif //RESOLVE_HPP
|
#endif //RESOLVE_HPP
|
||||||
|
|
|
||||||
|
|
@ -76,8 +76,6 @@ extern std::string g_origin;
|
||||||
|
|
||||||
cmd* make_cmd(std::vector<std::string> args);
|
cmd* make_cmd(std::vector<std::string> args);
|
||||||
|
|
||||||
bool add_include(std::string const& file);
|
|
||||||
|
|
||||||
class _obj
|
class _obj
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
|
|
|
||||||
|
|
@ -18,6 +18,9 @@
|
||||||
|
|
||||||
extern std::string indenting_string;
|
extern std::string indenting_string;
|
||||||
|
|
||||||
|
std::string basename(std::string const& in);
|
||||||
|
std::string dirname(std::string const& in);
|
||||||
|
|
||||||
std::string indent(int n);
|
std::string indent(int n);
|
||||||
|
|
||||||
std::vector<std::string> split(std::string const& in, const char* splitters);
|
std::vector<std::string> split(std::string const& in, const char* splitters);
|
||||||
|
|
|
||||||
|
|
@ -6,8 +6,6 @@
|
||||||
#include "options.hpp"
|
#include "options.hpp"
|
||||||
#include "parse.hpp"
|
#include "parse.hpp"
|
||||||
|
|
||||||
std::vector<std::string> included;
|
|
||||||
|
|
||||||
bool is_sub_special_cmd(std::string in)
|
bool is_sub_special_cmd(std::string in)
|
||||||
{
|
{
|
||||||
return in == "%include_sub" || in == "%resolve_sub";
|
return in == "%include_sub" || in == "%resolve_sub";
|
||||||
|
|
@ -111,18 +109,6 @@ std::string list::generate(int ind, bool first_indent)
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool add_include(std::string const& file)
|
|
||||||
{
|
|
||||||
std::string truepath=ztd::exec("readlink", "-f", file).first;
|
|
||||||
for(auto it: included)
|
|
||||||
{
|
|
||||||
if(it == truepath)
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
included.push_back(truepath);
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
// BLOCK
|
// BLOCK
|
||||||
|
|
||||||
std::string block::generate_redirs(int ind)
|
std::string block::generate_redirs(int ind)
|
||||||
|
|
|
||||||
|
|
@ -86,7 +86,7 @@ int main(int argc, char* argv[])
|
||||||
// do parsing
|
// do parsing
|
||||||
for(uint32_t i=0 ; i<args.size() ; i++)
|
for(uint32_t i=0 ; i<args.size() ; i++)
|
||||||
{
|
{
|
||||||
std::string& file = args[i];
|
std::string file = args[i];
|
||||||
std::string filecontents=import_file(file);
|
std::string filecontents=import_file(file);
|
||||||
// parse
|
// parse
|
||||||
g_origin=file;
|
g_origin=file;
|
||||||
|
|
@ -98,7 +98,7 @@ int main(int argc, char* argv[])
|
||||||
{
|
{
|
||||||
first_run=false;
|
first_run=false;
|
||||||
// resolve shebang
|
// resolve shebang
|
||||||
bool shebang_is_bin = ztd::exec("basename", argv[0]).first == ztd::exec("basename", tsh->shebang).first;
|
bool shebang_is_bin = basename(argv[0]) == basename(tsh->shebang);
|
||||||
if(shebang_is_bin)
|
if(shebang_is_bin)
|
||||||
tsh->shebang="#!/bin/sh";
|
tsh->shebang="#!/bin/sh";
|
||||||
|
|
||||||
|
|
@ -112,7 +112,6 @@ int main(int argc, char* argv[])
|
||||||
|
|
||||||
if(!is_exec && args.size() > 1) // not exec: parse options on args
|
if(!is_exec && args.size() > 1) // not exec: parse options on args
|
||||||
{
|
{
|
||||||
std::string t=args[0];
|
|
||||||
args=options.process(args);
|
args=options.process(args);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -123,7 +122,9 @@ int main(int argc, char* argv[])
|
||||||
/* mid processing */
|
/* mid processing */
|
||||||
// resolve/include
|
// resolve/include
|
||||||
if(g_include || g_resolve)
|
if(g_include || g_resolve)
|
||||||
|
{
|
||||||
resolve(tsh);
|
resolve(tsh);
|
||||||
|
}
|
||||||
|
|
||||||
// concatenate to main
|
// concatenate to main
|
||||||
sh->concat(tsh);
|
sh->concat(tsh);
|
||||||
|
|
@ -180,7 +181,7 @@ int main(int argc, char* argv[])
|
||||||
printFormatError(e);
|
printFormatError(e);
|
||||||
return 100;
|
return 100;
|
||||||
}
|
}
|
||||||
catch(std::exception& e)
|
catch(std::runtime_error& e)
|
||||||
{
|
{
|
||||||
if(tsh != nullptr)
|
if(tsh != nullptr)
|
||||||
delete tsh;
|
delete tsh;
|
||||||
|
|
|
||||||
|
|
@ -87,10 +87,10 @@ std::string get_varname(subarg* in)
|
||||||
|
|
||||||
/** VAR RECURSE **/
|
/** VAR RECURSE **/
|
||||||
|
|
||||||
void get_map_varname(_obj* in, std::map<std::string,uint32_t>* variable_map)
|
bool get_map_varname(_obj* in, std::map<std::string,uint32_t>* variable_map)
|
||||||
{
|
{
|
||||||
if(variable_map == nullptr)
|
if(variable_map == nullptr)
|
||||||
return;
|
return false;
|
||||||
switch(in->type)
|
switch(in->type)
|
||||||
{
|
{
|
||||||
case _obj::subarg_variable: {
|
case _obj::subarg_variable: {
|
||||||
|
|
@ -122,9 +122,10 @@ void get_map_varname(_obj* in, std::map<std::string,uint32_t>* variable_map)
|
||||||
}; break;
|
}; break;
|
||||||
default: break;
|
default: break;
|
||||||
}
|
}
|
||||||
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
void replace_varname(_obj* in, std::map<std::string,std::string>* varmap)
|
bool replace_varname(_obj* in, std::map<std::string,std::string>* varmap)
|
||||||
{
|
{
|
||||||
switch(in->type)
|
switch(in->type)
|
||||||
{
|
{
|
||||||
|
|
@ -170,15 +171,13 @@ void replace_varname(_obj* in, std::map<std::string,std::string>* varmap)
|
||||||
}; break;
|
}; break;
|
||||||
default: break;
|
default: break;
|
||||||
}
|
}
|
||||||
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
/** FCT RECURSE **/
|
/** FCT RECURSE **/
|
||||||
|
|
||||||
void get_map_cmd(_obj* in, std::map<std::string,uint32_t>* all_cmds)
|
bool get_map_cmd(_obj* in, std::map<std::string,uint32_t>* all_cmds)
|
||||||
{
|
{
|
||||||
if(all_cmds == nullptr)
|
|
||||||
return;
|
|
||||||
|
|
||||||
switch(in->type)
|
switch(in->type)
|
||||||
{
|
{
|
||||||
case _obj::block_cmd: {
|
case _obj::block_cmd: {
|
||||||
|
|
@ -189,12 +188,11 @@ void get_map_cmd(_obj* in, std::map<std::string,uint32_t>* all_cmds)
|
||||||
}; break;
|
}; break;
|
||||||
default: break;
|
default: break;
|
||||||
}
|
}
|
||||||
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
void get_map_fctname(_obj* in, std::map<std::string,uint32_t>* fct_map)
|
bool get_map_fctname(_obj* in, std::map<std::string,uint32_t>* fct_map)
|
||||||
{
|
{
|
||||||
if(fct_map == nullptr)
|
|
||||||
return;
|
|
||||||
switch(in->type)
|
switch(in->type)
|
||||||
{
|
{
|
||||||
case _obj::block_function: {
|
case _obj::block_function: {
|
||||||
|
|
@ -204,9 +202,10 @@ void get_map_fctname(_obj* in, std::map<std::string,uint32_t>* fct_map)
|
||||||
}; break;
|
}; break;
|
||||||
default: break;
|
default: break;
|
||||||
}
|
}
|
||||||
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
void replace_fctname(_obj* in, std::map<std::string,std::string>* fctmap)
|
bool replace_fctname(_obj* in, std::map<std::string,std::string>* fctmap)
|
||||||
{
|
{
|
||||||
switch(in->type)
|
switch(in->type)
|
||||||
{
|
{
|
||||||
|
|
@ -228,9 +227,10 @@ void replace_fctname(_obj* in, std::map<std::string,std::string>* fctmap)
|
||||||
}; break;
|
}; break;
|
||||||
default: break;
|
default: break;
|
||||||
}
|
}
|
||||||
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
void delete_fcts(_obj* in, std::set<std::string>* fcts)
|
bool delete_fcts(_obj* in, std::set<std::string>* fcts)
|
||||||
{
|
{
|
||||||
switch(in->type)
|
switch(in->type)
|
||||||
{
|
{
|
||||||
|
|
@ -253,6 +253,7 @@ void delete_fcts(_obj* in, std::set<std::string>* fcts)
|
||||||
}
|
}
|
||||||
default: break;
|
default: break;
|
||||||
}
|
}
|
||||||
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
/** name things **/
|
/** name things **/
|
||||||
|
|
@ -366,7 +367,7 @@ void delete_unused_fct(_obj* in, std::regex exclude)
|
||||||
recurse(delete_fcts, in, &unused);
|
recurse(delete_fcts, in, &unused);
|
||||||
}
|
}
|
||||||
|
|
||||||
void list_stuff(_obj* in, std::regex exclude, void (&fct)(_obj*,std::map<std::string,uint32_t>*) )
|
void list_stuff(_obj* in, std::regex exclude, bool (&fct)(_obj*,std::map<std::string,uint32_t>*) )
|
||||||
{
|
{
|
||||||
std::map<std::string,uint32_t> map;
|
std::map<std::string,uint32_t> map;
|
||||||
recurse(fct, in, &map);
|
recurse(fct, in, &map);
|
||||||
|
|
|
||||||
|
|
@ -243,7 +243,9 @@ std::pair<arg*, uint32_t> parse_arg(const char* in, uint32_t size, uint32_t star
|
||||||
else if( word_eq("$((", in, size, i) ) // arithmetic operation
|
else if( word_eq("$((", in, size, i) ) // arithmetic operation
|
||||||
{
|
{
|
||||||
// add previous subarg
|
// add previous subarg
|
||||||
ret->sa.push_back(new string_subarg(std::string(in+j, i-j)));
|
std::string tmpstr=std::string(in+j, i-j);
|
||||||
|
if(tmpstr!="")
|
||||||
|
ret->sa.push_back(new string_subarg(tmpstr));
|
||||||
// get arithmetic
|
// get arithmetic
|
||||||
auto r=parse_arithmetic(in, size, i+3);
|
auto r=parse_arithmetic(in, size, i+3);
|
||||||
ret->sa.push_back(r.first);
|
ret->sa.push_back(r.first);
|
||||||
|
|
@ -252,7 +254,9 @@ std::pair<arg*, uint32_t> parse_arg(const char* in, uint32_t size, uint32_t star
|
||||||
else if( word_eq("$(", in, size, i) ) // substitution
|
else if( word_eq("$(", in, size, i) ) // substitution
|
||||||
{
|
{
|
||||||
// add previous subarg
|
// add previous subarg
|
||||||
ret->sa.push_back(new string_subarg(std::string(in+j, i-j)));
|
std::string tmpstr=std::string(in+j, i-j);
|
||||||
|
if(tmpstr!="")
|
||||||
|
ret->sa.push_back(new string_subarg(tmpstr));
|
||||||
// get subshell
|
// get subshell
|
||||||
auto r=parse_subshell(in, size, i+2);
|
auto r=parse_subshell(in, size, i+2);
|
||||||
ret->sa.push_back(new subshell_subarg(r.first, true));
|
ret->sa.push_back(new subshell_subarg(r.first, true));
|
||||||
|
|
@ -261,7 +265,9 @@ std::pair<arg*, uint32_t> parse_arg(const char* in, uint32_t size, uint32_t star
|
||||||
else if( word_eq("${", in, size, i) ) // variable manipulation
|
else if( word_eq("${", in, size, i) ) // variable manipulation
|
||||||
{
|
{
|
||||||
// add previous subarg
|
// add previous subarg
|
||||||
ret->sa.push_back(new string_subarg(std::string(in+j, i-j)));
|
std::string tmpstr=std::string(in+j, i-j);
|
||||||
|
if(tmpstr!="")
|
||||||
|
ret->sa.push_back(new string_subarg(tmpstr));
|
||||||
// get manipulation
|
// get manipulation
|
||||||
auto r=parse_manipulation(in, size, i+2);
|
auto r=parse_manipulation(in, size, i+2);
|
||||||
ret->sa.push_back(r.first);
|
ret->sa.push_back(r.first);
|
||||||
|
|
@ -273,7 +279,9 @@ std::pair<arg*, uint32_t> parse_arg(const char* in, uint32_t size, uint32_t star
|
||||||
if(r.second > i+1)
|
if(r.second > i+1)
|
||||||
{
|
{
|
||||||
// add previous subarg
|
// add previous subarg
|
||||||
ret->sa.push_back(new string_subarg(std::string(in+j, i-j)));
|
std::string tmpstr=std::string(in+j, i-j);
|
||||||
|
if(tmpstr!="")
|
||||||
|
ret->sa.push_back(new string_subarg(tmpstr));
|
||||||
// add varname
|
// add varname
|
||||||
ret->sa.push_back(new variable_subarg(r.first));
|
ret->sa.push_back(new variable_subarg(r.first));
|
||||||
j = i = r.second;
|
j = i = r.second;
|
||||||
|
|
@ -302,7 +310,9 @@ std::pair<arg*, uint32_t> parse_arg(const char* in, uint32_t size, uint32_t star
|
||||||
else if( word_eq("$((", in, size, i) ) // arithmetic operation
|
else if( word_eq("$((", in, size, i) ) // arithmetic operation
|
||||||
{
|
{
|
||||||
// add previous subarg
|
// add previous subarg
|
||||||
ret->sa.push_back(new string_subarg(std::string(in+j, i-j)));
|
std::string tmpstr=std::string(in+j, i-j);
|
||||||
|
if(tmpstr!="")
|
||||||
|
ret->sa.push_back(new string_subarg(tmpstr));
|
||||||
// get arithmetic
|
// get arithmetic
|
||||||
auto r=parse_arithmetic(in, size, i+3);
|
auto r=parse_arithmetic(in, size, i+3);
|
||||||
ret->sa.push_back(r.first);
|
ret->sa.push_back(r.first);
|
||||||
|
|
@ -311,7 +321,9 @@ std::pair<arg*, uint32_t> parse_arg(const char* in, uint32_t size, uint32_t star
|
||||||
else if( word_eq("$(", in, size, i) ) // substitution
|
else if( word_eq("$(", in, size, i) ) // substitution
|
||||||
{
|
{
|
||||||
// add previous subarg
|
// add previous subarg
|
||||||
ret->sa.push_back(new string_subarg(std::string(in+j, i-j)));
|
std::string tmpstr=std::string(in+j, i-j);
|
||||||
|
if(tmpstr!="")
|
||||||
|
ret->sa.push_back(new string_subarg(tmpstr));
|
||||||
// get subshell
|
// get subshell
|
||||||
auto r=parse_subshell(in, size, i+2);
|
auto r=parse_subshell(in, size, i+2);
|
||||||
ret->sa.push_back(new subshell_subarg(r.first, false));
|
ret->sa.push_back(new subshell_subarg(r.first, false));
|
||||||
|
|
@ -320,7 +332,9 @@ std::pair<arg*, uint32_t> parse_arg(const char* in, uint32_t size, uint32_t star
|
||||||
else if( word_eq("${", in, size, i) ) // variable manipulation
|
else if( word_eq("${", in, size, i) ) // variable manipulation
|
||||||
{
|
{
|
||||||
// add previous subarg
|
// add previous subarg
|
||||||
ret->sa.push_back(new string_subarg(std::string(in+j, i-j)));
|
std::string tmpstr=std::string(in+j, i-j);
|
||||||
|
if(tmpstr!="")
|
||||||
|
ret->sa.push_back(new string_subarg(tmpstr));
|
||||||
// get manipulation
|
// get manipulation
|
||||||
auto r=parse_manipulation(in, size, i+2);
|
auto r=parse_manipulation(in, size, i+2);
|
||||||
ret->sa.push_back(r.first);
|
ret->sa.push_back(r.first);
|
||||||
|
|
@ -332,7 +346,9 @@ std::pair<arg*, uint32_t> parse_arg(const char* in, uint32_t size, uint32_t star
|
||||||
if(r.second > i+1)
|
if(r.second > i+1)
|
||||||
{
|
{
|
||||||
// add previous subarg
|
// add previous subarg
|
||||||
ret->sa.push_back(new string_subarg(std::string(in+j, i-j)));
|
std::string tmpstr=std::string(in+j, i-j);
|
||||||
|
if(tmpstr!="")
|
||||||
|
ret->sa.push_back(new string_subarg(tmpstr));
|
||||||
// add varname
|
// add varname
|
||||||
ret->sa.push_back(new variable_subarg(r.first));
|
ret->sa.push_back(new variable_subarg(r.first));
|
||||||
j = i = r.second;
|
j = i = r.second;
|
||||||
|
|
@ -346,7 +362,8 @@ std::pair<arg*, uint32_t> parse_arg(const char* in, uint32_t size, uint32_t star
|
||||||
|
|
||||||
// add string subarg
|
// add string subarg
|
||||||
std::string val=std::string(in+j, i-j);
|
std::string val=std::string(in+j, i-j);
|
||||||
ret->sa.push_back(new string_subarg(val));
|
if(val != "")
|
||||||
|
ret->sa.push_back(new string_subarg(val));
|
||||||
|
|
||||||
}
|
}
|
||||||
catch(ztd::format_error& e)
|
catch(ztd::format_error& e)
|
||||||
|
|
|
||||||
125
src/resolve.cpp
125
src/resolve.cpp
|
|
@ -7,29 +7,45 @@
|
||||||
#include "options.hpp"
|
#include "options.hpp"
|
||||||
#include "util.hpp"
|
#include "util.hpp"
|
||||||
#include "parse.hpp"
|
#include "parse.hpp"
|
||||||
|
#include "timer.hpp"
|
||||||
|
|
||||||
|
std::vector<std::string> included;
|
||||||
|
|
||||||
// -- CD STUFF --
|
// -- CD STUFF --
|
||||||
|
|
||||||
std::string pwd()
|
std::string pwd()
|
||||||
{
|
{
|
||||||
char buf[2048];
|
char buf[2048];
|
||||||
if(getcwd(buf, 2048) != NULL)
|
if(getcwd(buf, 2048) == NULL)
|
||||||
{
|
{
|
||||||
std::string ret=ztd::exec("pwd").first; // getcwd failed: call pwd
|
throw std::runtime_error("getcwd failed with errno "+std::to_string(errno));
|
||||||
ret.pop_back();
|
|
||||||
return ret;
|
|
||||||
}
|
}
|
||||||
return std::string(buf);
|
return std::string(buf);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
bool add_include(std::string const& file)
|
||||||
|
{
|
||||||
|
std::string truepath;
|
||||||
|
if(file[0] == '/')
|
||||||
|
truepath = file;
|
||||||
|
else
|
||||||
|
truepath=pwd() + '/' + file;
|
||||||
|
for(auto it: included)
|
||||||
|
{
|
||||||
|
if(it == truepath)
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
included.push_back(truepath);
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
// returns path to old dir
|
// returns path to old dir
|
||||||
std::string _pre_cd(shmain* parent)
|
std::string _pre_cd(shmain* parent)
|
||||||
{
|
{
|
||||||
if(parent->is_dev_file() || parent->filename == "")
|
if(parent->is_dev_file() || parent->filename == "")
|
||||||
return "";
|
return "";
|
||||||
std::string dir=pwd();
|
std::string dir=pwd();
|
||||||
std::string cddir=ztd::exec("dirname", parent->filename).first;
|
std::string cddir=dirname(parent->filename);
|
||||||
cddir.pop_back();
|
|
||||||
if(chdir(cddir.c_str()) != 0)
|
if(chdir(cddir.c_str()) != 0)
|
||||||
throw std::runtime_error("Cannot cd to '"+cddir+"'");
|
throw std::runtime_error("Cannot cd to '"+cddir+"'");
|
||||||
return dir;
|
return dir;
|
||||||
|
|
@ -47,8 +63,6 @@ void _cd(std::string const& dir)
|
||||||
std::vector<std::pair<std::string, std::string>> do_include_raw(condlist* cmd, shmain* parent, std::string* ex_dir=nullptr)
|
std::vector<std::pair<std::string, std::string>> do_include_raw(condlist* cmd, shmain* parent, std::string* ex_dir=nullptr)
|
||||||
{
|
{
|
||||||
std::vector<std::pair<std::string, std::string>> ret;
|
std::vector<std::pair<std::string, std::string>> ret;
|
||||||
if(!g_include)
|
|
||||||
return ret;
|
|
||||||
|
|
||||||
ztd::option_set opts = create_include_opts();
|
ztd::option_set opts = create_include_opts();
|
||||||
std::vector<std::string> rargs;
|
std::vector<std::string> rargs;
|
||||||
|
|
@ -73,14 +87,16 @@ std::vector<std::pair<std::string, std::string>> do_include_raw(condlist* cmd, s
|
||||||
for(auto it: rargs)
|
for(auto it: rargs)
|
||||||
command += it + ' ';
|
command += it + ' ';
|
||||||
command += "; do echo $I ; done";
|
command += "; do echo $I ; done";
|
||||||
std::string inc=ztd::sh(command);
|
std::string inc=ztd::sh(command); /* takes 1ms */
|
||||||
|
|
||||||
auto v = split(inc, '\n');
|
auto v = split(inc, '\n');
|
||||||
|
|
||||||
for(auto it: v)
|
for(auto it: v)
|
||||||
{
|
{
|
||||||
if(opts['f'] || add_include(it))
|
if(opts['f'] || add_include(it))
|
||||||
|
{
|
||||||
ret.push_back(std::make_pair(it, import_file(it)));
|
ret.push_back(std::make_pair(it, import_file(it)));
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if(ex_dir==nullptr)
|
if(ex_dir==nullptr)
|
||||||
|
|
@ -92,13 +108,10 @@ std::vector<std::pair<std::string, std::string>> do_include_raw(condlist* cmd, s
|
||||||
std::vector<condlist*> do_include_parse(condlist* cmd, shmain* parent)
|
std::vector<condlist*> do_include_parse(condlist* cmd, shmain* parent)
|
||||||
{
|
{
|
||||||
std::vector<condlist*> ret;
|
std::vector<condlist*> ret;
|
||||||
if(!g_include)
|
|
||||||
return ret;
|
|
||||||
|
|
||||||
std::string dir;
|
std::string dir;
|
||||||
auto incs=do_include_raw(cmd, parent, &dir);
|
auto incs=do_include_raw(cmd, parent, &dir);
|
||||||
|
|
||||||
|
|
||||||
for(auto it: incs)
|
for(auto it: incs)
|
||||||
{
|
{
|
||||||
shmain* sh=parse_text(it.second, it.first);
|
shmain* sh=parse_text(it.second, it.first);
|
||||||
|
|
@ -119,8 +132,6 @@ std::vector<condlist*> do_include_parse(condlist* cmd, shmain* parent)
|
||||||
std::pair<std::string, std::string> do_resolve_raw(condlist* cmd, shmain* parent, std::string* ex_dir=nullptr)
|
std::pair<std::string, std::string> do_resolve_raw(condlist* cmd, shmain* parent, std::string* ex_dir=nullptr)
|
||||||
{
|
{
|
||||||
std::pair<std::string, std::string> ret;
|
std::pair<std::string, std::string> ret;
|
||||||
if(!g_resolve)
|
|
||||||
return ret;
|
|
||||||
|
|
||||||
ztd::option_set opts = create_resolve_opts();
|
ztd::option_set opts = create_resolve_opts();
|
||||||
std::vector<std::string> rargs;
|
std::vector<std::string> rargs;
|
||||||
|
|
@ -169,8 +180,6 @@ std::pair<std::string, std::string> do_resolve_raw(condlist* cmd, shmain* parent
|
||||||
std::vector<condlist*> do_resolve_parse(condlist* cmd, shmain* parent)
|
std::vector<condlist*> do_resolve_parse(condlist* cmd, shmain* parent)
|
||||||
{
|
{
|
||||||
std::vector<condlist*> ret;
|
std::vector<condlist*> ret;
|
||||||
if(!g_resolve)
|
|
||||||
return ret;
|
|
||||||
|
|
||||||
std::pair<std::string,std::string> p;
|
std::pair<std::string,std::string> p;
|
||||||
try
|
try
|
||||||
|
|
@ -199,26 +208,27 @@ std::vector<condlist*> do_resolve_parse(condlist* cmd, shmain* parent)
|
||||||
|
|
||||||
// -- OBJECT CALLS --
|
// -- OBJECT CALLS --
|
||||||
|
|
||||||
std::vector<condlist*> resolve_condlist(condlist* in, shmain* parent)
|
std::pair< std::vector<condlist*> , bool > resolve_condlist(condlist* in, shmain* parent)
|
||||||
{
|
{
|
||||||
cmd* tc = in->first_cmd();
|
cmd* tc = in->first_cmd();
|
||||||
if(tc == nullptr)
|
if(tc == nullptr)
|
||||||
return std::vector<condlist*>();
|
return std::make_pair(std::vector<condlist*>(), false);
|
||||||
|
|
||||||
std::string const& strcmd=tc->firstarg_string();
|
std::string const& strcmd=tc->firstarg_string();
|
||||||
|
|
||||||
if(strcmd == "%include")
|
if(g_include && strcmd == "%include")
|
||||||
return do_include_parse(in, parent);
|
return std::make_pair(do_include_parse(in, parent), true);
|
||||||
else if(strcmd == "%resolve")
|
else if(g_resolve && strcmd == "%resolve")
|
||||||
return do_resolve_parse(in, parent);
|
return std::make_pair(do_resolve_parse(in, parent), true);
|
||||||
else
|
else
|
||||||
return std::vector<condlist*>();
|
return std::make_pair(std::vector<condlist*>(), false);
|
||||||
}
|
}
|
||||||
|
|
||||||
std::vector<arg*> resolve_arg(arg* in, shmain* parent, bool forcequote=false)
|
std::pair< std::vector<arg*> , bool > resolve_arg(arg* in, shmain* parent, bool forcequote=false)
|
||||||
{
|
{
|
||||||
std::vector<arg*> ret;
|
std::vector<arg*> ret;
|
||||||
arg* ta=nullptr;
|
arg* ta=nullptr;
|
||||||
|
bool has_resolved=false;
|
||||||
uint32_t j=0;
|
uint32_t j=0;
|
||||||
for(uint32_t i=0 ; i<in->sa.size() ; i++)
|
for(uint32_t i=0 ; i<in->sa.size() ; i++)
|
||||||
{
|
{
|
||||||
|
|
@ -234,18 +244,21 @@ std::vector<arg*> resolve_arg(arg* in, shmain* parent, bool forcequote=false)
|
||||||
continue;
|
continue;
|
||||||
std::string strcmd=c->firstarg_string();
|
std::string strcmd=c->firstarg_string();
|
||||||
std::string fulltext;
|
std::string fulltext;
|
||||||
if(strcmd == "%include")
|
if(g_include && strcmd == "%include")
|
||||||
{
|
{
|
||||||
for(auto it: do_include_raw(tc, parent) )
|
for(auto it: do_include_raw(tc, parent) )
|
||||||
fulltext += it.second;
|
fulltext += it.second;
|
||||||
}
|
}
|
||||||
else if(strcmd == "%resolve")
|
else if(g_resolve && strcmd == "%resolve")
|
||||||
{
|
{
|
||||||
fulltext = do_resolve_raw(tc, parent).second;
|
fulltext = do_resolve_raw(tc, parent).second;
|
||||||
}
|
}
|
||||||
else // skip
|
else // skip
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
|
// start of resolve
|
||||||
|
has_resolved = true;
|
||||||
|
|
||||||
if(tsh->quoted || forcequote)
|
if(tsh->quoted || forcequote)
|
||||||
{
|
{
|
||||||
stringReplace(fulltext, "\"", "\\\"");
|
stringReplace(fulltext, "\"", "\\\"");
|
||||||
|
|
@ -301,34 +314,42 @@ std::vector<arg*> resolve_arg(arg* in, shmain* parent, bool forcequote=false)
|
||||||
delete ta;
|
delete ta;
|
||||||
in->sa.resize(0);
|
in->sa.resize(0);
|
||||||
}
|
}
|
||||||
return ret;
|
return std::make_pair(ret, has_resolved);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
// -- RECURSIVE CALL --
|
// -- RECURSIVE CALL --
|
||||||
|
|
||||||
void resolve_recurse(_obj* o, shmain* parent)
|
bool resolve_recurse(_obj* o, shmain* parent)
|
||||||
{
|
{
|
||||||
switch(o->type)
|
switch(o->type)
|
||||||
{
|
{
|
||||||
|
// in case of applicable object:
|
||||||
|
// check every sub-object
|
||||||
|
// execute resolve manually
|
||||||
|
// instruct parent resolve to not resolve
|
||||||
case _obj::_list :
|
case _obj::_list :
|
||||||
{
|
{
|
||||||
auto t = dynamic_cast<list*>(o);
|
auto t = dynamic_cast<list*>(o);
|
||||||
for(uint32_t i=0 ; i<t->cls.size() ; i++)
|
for(uint32_t i=0 ; i<t->cls.size() ; i++)
|
||||||
{
|
{
|
||||||
std::vector<condlist*> r=resolve_condlist(t->cls[i], parent);
|
auto r=resolve_condlist(t->cls[i], parent);
|
||||||
if(r.size()>0)
|
if(r.second)
|
||||||
{
|
{
|
||||||
// add new cls after current
|
// add new cls after current
|
||||||
t->cls.insert(t->cls.begin()+i+1, r.begin(), r.end());
|
t->cls.insert(t->cls.begin()+i+1, r.first.begin(), r.first.end());
|
||||||
// delete current
|
// delete current
|
||||||
delete t->cls[i];
|
delete t->cls[i];
|
||||||
t->cls.erase(t->cls.begin()+i);
|
t->cls.erase(t->cls.begin()+i);
|
||||||
// back to previous object
|
// skip to after inserted cls
|
||||||
i--;
|
i += r.first.size()-1;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
resolve(t->cls[i], parent);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
// list
|
return false;
|
||||||
} break;
|
} break;
|
||||||
case _obj::_arglist :
|
case _obj::_arglist :
|
||||||
{
|
{
|
||||||
|
|
@ -336,24 +357,33 @@ void resolve_recurse(_obj* o, shmain* parent)
|
||||||
for(uint32_t i=0 ; i<t->args.size() ; i++)
|
for(uint32_t i=0 ; i<t->args.size() ; i++)
|
||||||
{
|
{
|
||||||
auto r=resolve_arg(t->args[i], parent);
|
auto r=resolve_arg(t->args[i], parent);
|
||||||
if(r.size()>0)
|
if(r.first.size()>0)
|
||||||
{
|
{
|
||||||
// add new args
|
// add new args
|
||||||
t->args.insert(t->args.begin()+i+1, r.begin(), r.end());
|
t->args.insert(t->args.begin()+i+1, r.first.begin(), r.first.end());
|
||||||
// delete current
|
// delete current
|
||||||
delete t->args[i];
|
delete t->args[i];
|
||||||
t->args.erase(t->args.begin()+i);
|
t->args.erase(t->args.begin()+i);
|
||||||
i += r.size()-1;
|
i += r.first.size()-1;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
resolve(t->args[i], parent);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
// arglist
|
return false;
|
||||||
return;
|
|
||||||
} break;
|
} break;
|
||||||
case _obj::block_cmd :
|
case _obj::block_cmd :
|
||||||
{
|
{
|
||||||
auto t = dynamic_cast<cmd*>(o);
|
auto t = dynamic_cast<cmd*>(o);
|
||||||
for(auto it: t->var_assigns)
|
for(auto it: t->var_assigns) // var assigns
|
||||||
|
{
|
||||||
resolve_arg(it.second, parent, true); // force quoted
|
resolve_arg(it.second, parent, true); // force quoted
|
||||||
|
resolve(it.second, parent);
|
||||||
|
}
|
||||||
|
resolve(t->redirs, parent);
|
||||||
|
resolve(t->args, parent);
|
||||||
|
return false;
|
||||||
}; break;
|
}; break;
|
||||||
case _obj::block_case :
|
case _obj::block_case :
|
||||||
{
|
{
|
||||||
|
|
@ -361,18 +391,27 @@ void resolve_recurse(_obj* o, shmain* parent)
|
||||||
for(auto sc: t->cases)
|
for(auto sc: t->cases)
|
||||||
{
|
{
|
||||||
resolve_arg(t->carg, parent, true); // force quoted
|
resolve_arg(t->carg, parent, true); // force quoted
|
||||||
|
resolve(t->carg, parent);
|
||||||
|
|
||||||
|
for(auto it: sc.first)
|
||||||
{
|
{
|
||||||
for(auto it: sc.first)
|
resolve_arg(it, parent, true); // force quoted
|
||||||
resolve_arg(it, parent, true); // force quoted
|
resolve(it, parent);
|
||||||
}
|
}
|
||||||
|
resolve(sc.second, parent);
|
||||||
}
|
}
|
||||||
}; break;
|
}; break;
|
||||||
default: break;
|
default: break;
|
||||||
}
|
}
|
||||||
return;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
// recursive call of resolve
|
// recursive call of resolve
|
||||||
|
void resolve(_obj* in, shmain* parent)
|
||||||
|
{
|
||||||
|
recurse(resolve_recurse, in, parent);
|
||||||
|
}
|
||||||
|
|
||||||
void resolve(shmain* sh)
|
void resolve(shmain* sh)
|
||||||
{
|
{
|
||||||
recurse(resolve_recurse, sh, sh);
|
recurse(resolve_recurse, sh, sh);
|
||||||
|
|
|
||||||
21
src/util.cpp
21
src/util.cpp
|
|
@ -20,6 +20,24 @@ std::string indent(int n)
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
std::string basename(std::string const& in)
|
||||||
|
{
|
||||||
|
size_t slr=in.rfind('/');
|
||||||
|
if(slr != std::string::npos)
|
||||||
|
return in.substr(slr);
|
||||||
|
else
|
||||||
|
return in;
|
||||||
|
}
|
||||||
|
|
||||||
|
std::string dirname(std::string const& in)
|
||||||
|
{
|
||||||
|
size_t slr=in.rfind('/');
|
||||||
|
if(slr != std::string::npos)
|
||||||
|
return in.substr(0,slr);
|
||||||
|
else
|
||||||
|
return ".";
|
||||||
|
}
|
||||||
|
|
||||||
std::vector<std::string> split(std::string const& in, const char* splitters)
|
std::vector<std::string> split(std::string const& in, const char* splitters)
|
||||||
{
|
{
|
||||||
uint32_t i=0,j=0;
|
uint32_t i=0,j=0;
|
||||||
|
|
@ -229,8 +247,7 @@ int execute(shmain* sh, std::vector<std::string>& args)
|
||||||
{
|
{
|
||||||
std::string data=sh->generate();
|
std::string data=sh->generate();
|
||||||
|
|
||||||
std::string filename=ztd::exec("basename", args[0]).first;
|
std::string filename = basename(args[0]);
|
||||||
filename.pop_back();
|
|
||||||
|
|
||||||
// generate path
|
// generate path
|
||||||
std::string tmpdir = (getenv("TMPDIR") != NULL) ? getenv("TMPDIR") : "/tmp" ;
|
std::string tmpdir = (getenv("TMPDIR") != NULL) ? getenv("TMPDIR") : "/tmp" ;
|
||||||
|
|
|
||||||
Loading…
Reference in a new issue