www.mikrocontroller.net

Forum: PC-Programmierung programmausgaben in string umleiten


Autor: andre (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
ich starte über ein c++ programm ein weiteres programm. dieses 
gestartete programm gibt fleissig output in die konsole. diesen output 
würde ich nun gerne in meinem programm als string verarbeiten.

welche möglichkeiten habe ich, den fremden konsolenouptut aufzufangen?

Autor: Klaus Wachtler (mfgkw)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Es gibt zum Einen die Möglichkeit, das Programm mit popen()
zu starten. Damit kann man wahlweise die Ein- oder die Ausgabe
umleiten.

Eine andere Variante, mit der beides gleichzeitig geht (und
vermutlich auch gleich stderr) ist es, das Programm mit system()
zu starten.
In der dort anzugebenden Kommandozeile kann man nach dem
Programmaufruf die Ein- und Ausgabe mit "... >&95 <&97"
mit Dateien verknüpfen, die im aufrufenden Prozeß die fd-Nummern
beispielsweise 95 und 97 haben.
Man öffnet also vorher die Dateien und trägt die fd-Nummern
mit sprintf() in die Kommandozeile ein.
Analog z.B. "... 2>&98 ..." für stderr (was mal unter
Windows 2000 bei mir geklappt hatte, unter XP irgendwann mal
nicht; ich habe es aber nicht weiter verfolgt).
Startet man das Programm zusätzlich mit einem & am Ende, kann
man während es läuft zu fd 97 etwas schreiben, was vom
Kindprozeß von stdin gelesen wird, und gleichzeitig von 95
bzw. 98 dessen Ausgabe lesen.

Dieser Weg ist etwas umständlicher, aber wesentlich flexibler.
Einfacher ist popen(), wenn es reicht.

Autor: Sven H. (dsb_sven)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Ich gehe mal davon aus, dass du die Möglichkeit hast, den standard 
output deines Programms abzufangen. In C# gehts über die Klasse Process, 
wenn ich mich nicht irre...

Autor: Klaus Wachtler (mfgkw)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
PS: es geht natürlich nur, wenn das Kind Standardein- und -ausgabe
verwendet.
Die Windows-eigenen Konsolenfunktionen lassen sich so nicht abfangen.

Autor: Max (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Falls das Programm  myprog.exe ist:

In der Konsole

myprog >Dateiname

eingeben.

z.B.
dir >d.txr

Autor: andre (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
die sache verhält sich im detail folgendermaßen. ich nutze um das 
programm zu öffnen die pstream lib welche auf popen aufsetzt. 
(http://pstreams.sourceforge.net/)

öffne ich damit als beispiel ifconfig:
std::string s, ausgabe;
redi::pstream ifconfig("ifconfig -a");
while(std::getline(ifconfig, s)) {
   ausgabe.append(s);
   ausgabe.append("\n");
}
textview_buffer->set_text(ausgabe);

landet der konsolenoutput wunderbar im string ausgabe und wird meinem 
gtk widget zugefügt.

ich will aber nicht ifconfig anzeigen. mein programm startet ein android 
sdk tool welches unterschiedliche parameter hat. mit einem der parameter 
geht es. dieser parameter öffnet eine shell zum android device und ich 
kann problemlos infos hin und her schieben
std::string s, ausgabe;
chdir(path_to_adb.c_str());
redi::pstream adb_shell("./adb shell");
adb_shell << "mount /system" << std::endl;
adb_shell << "chmod 644 /system/app/*" << std::endl;
adb_shell << "chmod 644 /system/framework/*" << std::endl;
adb_shell << "exit" << std::endl;
while(std::getline(adb_shell, s)) {
   ausgabe.append(s);
   ausgabe.append("\n");
   }
textview_buffer->set_text(ausgabe);

folgende anweisung geht aber nicht. dieses mal wird keine shell geöffnet 
sondern durch das android tool der inhalt eines ordners datei für datei 
gepushed.
std::string s, ausgabe;
std::string system_app;
std::string copy_apps;
system_app = "ls ";          
system_app.append(path_to_binary);
system_app.append("/system/app/");
redi::ipstream ls(system_app);
while (ls >> copy_apps) { 
   chdir(path_to_adb.c_str());
   std::string command = "./adb push ";
   command.append(path_to_binary);
   command.append("/system/app/");
   command.append(copy_apps);
   command.append(" /system/app/");
   redi::pstream adb_push(command);
   while(std::getline(adb_push, s)) {
      ausgabe.append(s);
      ausgabe.append("\n");
   }

   textview_buffer->set_text(ausgabe);
}

der unterschied zwischen der 2. und 3. anweisung ist eigentlich nur der, 
das adb shell eine dauerhafte verbindung aufbaut in welche ich schreiben 
und lesen kann. adb push hält keine verbindung offen. es kopiert die 
datei und damit ist die sache abgeharkt. aber auch adb push gibt auf der 
konsole output über die kopierten daten und wie lange es gedauert hat. 
ich komme halt nur nicht ran.

Autor: andre (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
hier noch mal das letzte listing in übersichtlich und ohne unnötigen 
schnick schnack
std::string s, ausgabe;
chdir(path_to_adb.c_str());  
redi::pstream adb_pull("./adb pull /system/app /home/dir/");
while(std::getline(adb_pull, s)) {
  ausgabe.append(s);
  ausgabe.append("\n");
}
textview_buffer->set_text(ausgabe);

adb mit dem parameter pull gibt mir also über die pstream lib keinen 
output zurück. schiebt aber trotzdem output in die konsole.

Autor: Klaus (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Du solltest mit etwas einfacherem anfangen! Wie wärs, wenn du dir als 
erstes Grundkenntnisse im Benutzen der Shift-Taste aneignest? Das übst 
du dann noch ein wenig, dann kommt der nächste Schritt.

Autor: andre (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
schlechten tag erwischt? sprich dich aus, das hilft dir vielleicht über 
deinen frust hinweg zu kommen...

Autor: kljdsghökh (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Wie glaubst Du den Compiler zur Zusammenarbeit zu ueberreden, wenn Du 
Dich nicht an dessen Regeln haeltst? Eben, da kannst Du dessen 
Rechtschreibung beachten.

Aber bei uns hier denkst Du, die sollen mir doch bloss helfen, deren 
Regeln interessieren mich einen Sch.....dreck.

Dann interessieren uns Deine Probleme eben noch weniger.

Gast

Antwort schreiben

Die Angabe einer E-Mail-Adresse ist freiwillig. Wenn Sie automatisch per E-Mail über Antworten auf Ihren Beitrag informiert werden möchten, melden Sie sich bitte an.

Wichtige Regeln - erst lesen, dann posten!

  • Groß- und Kleinschreibung verwenden
  • Längeren Sourcecode nicht im Text einfügen, sondern als Dateianhang

Formatierung (mehr Informationen...)

  • [c]C-Code[/c]
  • [avrasm]AVR-Assembler-Code[/avrasm]
  • [code]Code in anderen Sprachen, ASCII-Zeichnungen[/code]
  • [math]Formel in LaTeX-Syntax[/math]
  • [[Titel]] - Link zu Artikel
  • Verweis auf anderen Beitrag einfügen: Rechtsklick auf Beitragstitel,
    "Adresse kopieren", und in den Text einfügen




Bild automatisch verkleinern, falls nötig
Bitte das JPG-Format nur für Fotos und Scans verwenden!
Zeichnungen und Screenshots im PNG- oder
GIF-Format hochladen. Siehe Bildformate.
Hinweis: der ursprüngliche Beitrag ist mehr als 6 Monate alt.
Bitte hier nur auf die ursprüngliche Frage antworten,
für neue Fragen einen neuen Beitrag erstellen.

Mit dem Abschicken bestätigst du, die Nutzungsbedingungen anzuerkennen.