uu nie doczytałem
el.pescado pisze:Mój pomysł na pobieranie znaku zachęty (bez rozwijania specjalnych symboli) - uruchomić basha każąc mu wypisać zmienną $PS1 na wyjście komendą echo:
Kod: Zaznacz cały
#include <stdio.h>
#include <stdlib.h>
#define BUFFER_SIZE 1024
int main (int argc, char *argv[])
{
char buffer[BUFFER_SIZE];
FILE *p = popen ("sh -ic 'echo -n $PS1'", "r");
if (p == NULL) {
perror ("popen");
return EXIT_FAILURE;
}
while (fgets (buffer, BUFFER_SIZE, p))
;
pclose (p);
printf ("$PS1 = '%s'\n", buffer);
return EXIT_SUCCESS;
}
Kod: Zaznacz cały
$ gcc -Wall -o printps1 printps1.c
$ ./printps1
$PS1 = '\h:\w>'
EDIT:
PS. Dla lepszych efektów trzeba poeksperymentować z opcjami wywołania basha (-i, -l) - znak zachęty zależy od skryptów startowych basha, a to, które pliki startowe są ładowane podczas startu basha, zależne jest od opcji wywołania.
to rozwiązanie mi się podoba i działa tak jak bym mniej więcej chciał, zaraz zmodyfikuje to co przedstawiłem poniżej:)
Kod: Zaznacz cały
#include <iostream>
#include <stdlib.h>
#include <fstream>
#include <string>
#include <string.h>
#include <vector>
#include <time.h>
using namespace std;
void read_config_shell(const char * shell_file,string default_prompt);
string prompt();
void decode(string to_decode);
int main()
{
string shell=prompt();
shell+="p";
//system(shell.c_str());
return 0;
}
string prompt()
{
string shell_set;
string shell=getenv("SHELL");
if (shell=="/bin/bash")
{
read_config_shell(".bashrc","\\u@\\h:\\w$");
shell_set="bash -c ";
}
if (shell=="/bin/tsh")
read_config_shell(".cshrc",">");
if (shell=="/bin/sh")
read_config_shell(".profile","$");
if (shell=="/bin/csh")
read_config_shell(".cshrc",">");
if (shell=="/bin/zsh")
read_config_shell(".zprofile","['\'w]%");
return shell_set;
}
void read_config_shell(const char * shell_file,string default_prompt)
{
char * prompt=getenv("PS1");
if (prompt==NULL)
{
prompt=getenv("prompt");
if (prompt==NULL)
{
/*string st,prompt;//usunac prompt jak bedzie robiona dekodacja
vector<string>vec_s;
string home=getenv("HOME");
string sc_plik=home+"/"+shell_file;
ifstream plik(sc_plik.c_str());
if (!plik) return decode(default_prompt);
while (!plik.eof())
{
getline(plik,st);
char *wzr =new char[st.length()+1];
strcpy(wzr,st.c_str());
unsigned int j,n;
unsigned int ok=0;
for (j=0;j<st.length()+1;j++)
{
while(wzr[j]==' ') j++;
switch (wzr[j])
*
{
case 'p': ok++; break;
case 'r': ok++; break;
case 'o': ok++; break;
case 'm': ok++; break;
case 't': ok++; break;
case 'P': ok++; break;
case 'S': ok++; break;
case '1': ok++; break;
case '=': ok++; break;
default: ok=0;n=1;break;
}
if (((ok==4)&&(n==0))||((ok==7)&&(n==0)))
prompt=st;
if (n==1)
{
n=0;
break;
}
}
delete [] wzr;
vec_s.push_back(st);
decode(default_prompt);
}
if(prompt==NULL)
decode(default_prompt);
else
decode(prompt);
plik.close();*/
decode(default_prompt);
}
else decode(prompt);
}
else decode (prompt);
}
void decode(string to_decode)
{
int c;
struct tm *tm;
time_t the_time;
char timebuf[128];
string y;
int ile=to_decode.length()+1;
char *znak = new char [ile];
strcpy(znak,to_decode.c_str());
for (c=0; c<ile;c++,znak++)
{
//while(*znak==' ')znak++;
if (*znak=='\\')
{
znak++;
switch(*znak)
{
case 'u':
case 'U':
cout<<getenv("USER");
break;
case 'h':
case 'H':
{
cout<<getenv("HOSTNAME");
break;
}
case 'w':
case 'W':
{
string pwd=getenv("PWD");
string home=getenv("HOME");
char *pwd_char = new char [pwd.length()+1];
char *home_char = new char [home.length()+1];
strcpy(pwd_char,pwd.c_str());
strcpy(home_char,home.c_str());
unsigned int z;
string tmp;
for (z=0; z<home.length()+1;z++,pwd_char++,home_char++)
{
if (*home_char==*pwd_char) tmp="~";
}
if (tmp.empty()&&(z>6)) cout<<home; else
{
cout<<tmp;
unsigned int g;
pwd_char--;
for (g=z; g<pwd.length()+1;g++,pwd_char++)
{
cout<<*pwd_char;
}
}
break;
}
case 'd':
case 't':
case 'T':
case '@':
case 'A':
{
int n;
(void) time (&the_time);
tm=localtime(&the_time);
if (*znak=='d')
n=strftime(timebuf,sizeof(timebuf),"%a %b %d",tm);
if (*znak=='t')
n=strftime(timebuf,sizeof(timebuf), "%H:%M:%S",tm);
if (*znak=='T')
n=strftime(timebuf,sizeof(timebuf), "%I:%M:%S",tm);
if (*znak=='@')
n=strftime(timebuf,sizeof(timebuf), "%I:%M ",tm);
if (*znak=='A')
n=strftime(timebuf,sizeof(timebuf), "%H:%M",tm);
if ( n==0)
timebuf[0]='\0';
else
timebuf[sizeof(timebuf) -1] = '\0';
cout<<timebuf;
break;
}
default:break;
}
}else cout<<*znak;
}
cout<<endl;
}
Ja za to wymyśliłem jak na razie coś takiego.
W sles działa, w ubuntu wyświetla mi user@user@host: pwd
Kod: Zaznacz cały
#include <stdio.h>
#include <stdlib.h>
#include <iostream>
#include <string>
#include <string.h>
#include <time.h>
using namespace std;
#define BUFFER_SIZE 1024
string default_prompt;
int c,ile;
string detect_shell();
void decode(char* to_decode);
int main (int argc, char *argv[])
{
char buffer[BUFFER_SIZE];
string shell_seting=detect_shell();
string prompt_popen=shell_seting+" -ic 'echo -n $PS1'";
FILE *p = popen (prompt_popen.c_str(), "r");
if (p == NULL) {
perror ("popen");
return EXIT_FAILURE;
}
while (fgets (buffer, BUFFER_SIZE, p));
pclose (p);
decode(buffer);
return EXIT_SUCCESS;
}
string detect_shell()
{
string shell_set;
string shell=getenv("SHELL");
if (shell=="/bin/bash") shell_set="bash";
if (shell=="/bin/tsh") shell_set="tsh";
if (shell=="/bin/sh") shell_set="sh";
if (shell=="/bin/csh") shell_set="csh";
if (shell=="/bin/zsh") shell_set="zsh";
return shell_set;
}
void decode(char* to_decode)
{
int us,ho,ww,mal,yy;
struct tm *tm;
time_t the_time;
char timebuf[128];
string y;
us=0;
ho=0;
ww=0;
mal=0;
yy=0;
ile=strlen(to_decode);
for (c=0; c<=ile;c++)
{
//while(*znak==' ')znak++;
if (to_decode[c]=='\\')
{
c++;
switch(to_decode[c])
{
case 'u':
case 'U':
{
if(us==0)
cout<<getenv("USER");
us=1;
}
break;
case 'h':
case 'H':
cout<<getenv("HOST");
break;
case 'w':
case 'W':
{
if(ww==0)
{
char* pwd=getenv("PWD");
char* home=getenv("HOME");
unsigned int pwd_ile = strlen(pwd);
unsigned int home_ile =strlen(home);
unsigned int z;
string tmp;
for (z=0; z<home_ile;z++)
{
if (home[z]==pwd[z]) tmp="~";
}
if (tmp.empty()&&(z>6)) cout<<home;
else
{
cout<<tmp;
unsigned int g;
for (g=z; g<pwd_ile;g++)
{
cout<<pwd[g];
}
}
ww=1;
}
break;
}
case 'd':
case 't':
case 'T':
case '@':
case 'A':
{
int n;
(void) time (&the_time);
tm=localtime(&the_time);
if (to_decode[c]=='d')
n=strftime(timebuf,sizeof(timebuf),"%a %b %d",tm);
if (to_decode[c]=='t')
n=strftime(timebuf,sizeof(timebuf), "%H:%M:%S",tm);
if (to_decode[c]=='T')
n=strftime(timebuf,sizeof(timebuf), "%I:%M:%S",tm);
if (to_decode[c]=='@')
n=strftime(timebuf,sizeof(timebuf), "%I:%M ",tm);
if (to_decode[c]=='A')
n=strftime(timebuf,sizeof(timebuf), "%H:%M",tm);
if ( n==0)
timebuf[0]='\0';
else
timebuf[sizeof(timebuf) -1] = '\0';
cout<<timebuf;
break;
}
default:break;
}
}else
{
switch (to_decode[c])
{
case '0':
case '}':
case ']':
case ';':
break;
case ':':
{
if(yy==0)
{
cout<<to_decode[c];
yy=1;
}
break;
}
case '@':
{
if(mal==0)
{
cout<<to_decode[c];
mal=1;
}
break;
}
case '[':
case '{':
{
for (;c<=ile;c++)
{
if((to_decode[c]=='}')||(to_decode[c]==']')||to_decode[c]==')')
break;
}
break;
}
default: cout<<to_decode[c];
}
}
}
cout<<" ";
}
Dlaczego nie działa cout<<getenv("HOSTNAME");?
"Dopóki nie skorzystałem z internetu, nie wiedziałem że na świecie żyje tylu idiotów " - S.Lem.