Main Page | Namespace List | Class Hierarchy | Alphabetical List | Class List | Directories | File List | Namespace Members | Class Members | File Members | Related Pages

processinfo.cpp

Go to the documentation of this file.
00001 /**********************************************************************
00002 ** ProcessInfo
00003 **
00004 ** Display process information
00005 **
00006 ** Copyright (C) 2002, Dan Williams
00007 **                    williamsdr@acm.org
00008 **                    http://draknor.net
00009 **
00010 ** This file may be distributed and/or modified under the terms of the
00011 ** GNU General Public License version 2 as published by the Free Software
00012 ** Foundation and appearing in the file LICENSE.GPL included in the
00013 ** packaging of this file.
00014 **
00015 ** This file is provided AS IS with NO WARRANTY OF ANY KIND, INCLUDING THE
00016 ** WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
00017 **
00018 **********************************************************************/
00019 
00020 #include "processinfo.h"
00021 #include "detail.h"
00022 
00023 /* OPIE */
00024 #include <opie2/olistview.h>
00025 #include <qpe/qpeapplication.h>
00026 
00027 /* QT */
00028 #include <qcombobox.h>
00029 #include <qdir.h>
00030 #include <qlayout.h>
00031 #include <qmessagebox.h>
00032 #include <qpushbutton.h>
00033 #include <qtextview.h>
00034 #include <qtimer.h>
00035 #include <qwhatsthis.h>
00036 
00037 /* STD */
00038 #include <sys/types.h>
00039 #include <signal.h>
00040 
00041 using namespace Opie::Ui;
00042 ProcessInfo::ProcessInfo( QWidget* parent,  const char* name, WFlags fl )
00043         : QWidget( parent, name, fl )
00044 {
00045     QGridLayout *layout = new QGridLayout( this );
00046     layout->setSpacing( 4 );
00047     layout->setMargin( 4 );
00048 
00049 
00050     ProcessView = new OListView( this, "ProcessView" );
00051     int colnum = ProcessView->addColumn( tr( "PID" ) );
00052     ProcessView->setColumnAlignment( colnum, Qt::AlignRight );
00053     colnum = ProcessView->addColumn( tr( "Command" ),96 );
00054     colnum = ProcessView->addColumn( tr( "Status" ) );
00055     colnum = ProcessView->addColumn( tr( "Time" ) );
00056     ProcessView->setColumnAlignment( colnum, Qt::AlignRight );
00057     ProcessView->setAllColumnsShowFocus( TRUE );
00058     QPEApplication::setStylusOperation( ProcessView->viewport(), QPEApplication::RightOnHold );
00059     connect( ProcessView, SIGNAL( rightButtonPressed(QListViewItem*,const QPoint&,int) ),
00060              this, SLOT( viewProcess(QListViewItem*) ) );
00061     layout->addMultiCellWidget( ProcessView, 0, 0, 0, 1 );
00062     QWhatsThis::add( ProcessView, tr( "This is a list of all the processes on this handheld device.\n\nClick and hold on a process to see additional information about the process, or to send a signal to it." ) );
00063 
00064     SignalCB = new QComboBox( FALSE, this, "SignalCB" );
00065     SignalCB->insertItem( " 1: SIGHUP" );
00066     SignalCB->insertItem( " 2: SIGINT" );
00067     SignalCB->insertItem( " 3: SIGQUIT" );
00068     SignalCB->insertItem( " 5: SIGTRAP" );
00069     SignalCB->insertItem( " 6: SIGABRT" );
00070     SignalCB->insertItem( " 9: SIGKILL" );
00071     SignalCB->insertItem( "14: SIGALRM" );
00072     SignalCB->insertItem( "15: SIGTERM" );
00073     SignalCB->insertItem( "18: SIGCONT" );
00074     SignalCB->insertItem( "19: SIGSTOP" );
00075     layout->addWidget( SignalCB, 1, 0 );
00076     QWhatsThis::add( SignalCB, tr( "Select a signal here and then click the Send button to the right to send to this process." ) );
00077 
00078     SendButton = new QPushButton( this, "SendButton" );
00079     SendButton->setMinimumSize( QSize( 50, 24 ) );
00080     SendButton->setMaximumSize( QSize( 50, 24 ) );
00081     SendButton->setText( tr( "Send" ) );
00082     connect( SendButton, SIGNAL( clicked() ), this, SLOT( slotSendClicked() ) );
00083     layout->addWidget( SendButton, 1, 1 );
00084     QWhatsThis::add( SendButton, tr( "Click here to send the selected signal to this process." ) );
00085 
00086     QTimer *t = new QTimer( this );
00087     connect( t, SIGNAL( timeout() ), this, SLOT( updateData() ) );
00088     t->start( 5000 );
00089 
00090     updateData();
00091 
00092     ProcessDtl = new Detail();
00093     QWhatsThis::add( ProcessDtl->detailView, tr( "This area shows detailed information about this process." ) );
00094 }
00095 
00096 ProcessInfo::~ProcessInfo()
00097 {}
00098 
00099 void ProcessInfo::updateData()
00100 {
00101     int pid, ppid, pgrp, session, tty, tpgid, utime, stime, cutime, cstime, counter, priority, starttime,
00102     signal, blocked, sigignore, sigcatch;
00103     uint flags, minflt, cminflt, majflt, cmajflt, timeout, itrealvalue, vsize, rss, rlim, startcode,
00104     endcode, startstack, kstkesp, kstkeip, wchan;
00105     char state;
00106     char comm[64];
00107 
00108     QString selectedpid;
00109     OListViewItem *curritem = static_cast<OListViewItem*>( ProcessView->currentItem() );
00110     if ( curritem )
00111     {
00112         selectedpid = curritem->text( 0 );
00113     }
00114 
00115     ProcessView->clear();
00116 
00117     OListViewItem *newitem;
00118     OListViewItem *selecteditem = 0x0;
00119     QDir *procdir = new QDir("/proc", 0, QDir::Name, QDir::Dirs);
00120     QFileInfoList *proclist = new QFileInfoList(*(procdir->entryInfoList()));
00121     if ( proclist )
00122     {
00123         QFileInfoListIterator it(*proclist);
00124         QFileInfo *f;
00125         while ( ( f = it.current() ) != 0 )
00126         {
00127             ++it;
00128             QString processnum = f->fileName();
00129             if ( processnum >= "1" && processnum <= "99999" )
00130             {
00131                 FILE *procfile = fopen( ( QString ) ( "/proc/" + processnum + "/stat"), "r");
00132 
00133                 if ( procfile )
00134                 {
00135                     fscanf( procfile,
00136                             "%d %s %c %d %d %d %d %d %u %u %u %u %u %d %d %d %d %d %d %u %u %d %u %u %u %u %u %u %u %u %d %d %d %d %u",
00137                             &pid, comm, &state, &ppid, &pgrp, &session,&tty, &tpgid, &flags, &minflt, &cminflt,
00138                             &majflt, &cmajflt, &utime, &stime, &cutime, &cstime, &counter, &priority, &timeout,
00139                             &itrealvalue, &starttime, &vsize, &rss, &rlim, &startcode, &endcode, &startstack,
00140                             &kstkesp, &kstkeip, &signal, &blocked, &sigignore, &sigcatch, &wchan );
00141                     processnum = processnum.rightJustify( 5, ' ' );
00142                     QString processcmd = QString( comm ).replace( QRegExp( "[()]" ), "" );
00143                     QString processstatus = QChar(state);
00144                     QString processtime = QString::number( ( utime + stime ) / 100 );
00145                     processtime = processtime.rightJustify( 9, ' ' );
00146                     fclose( procfile );
00147 
00148                     newitem = new OListViewItem( ProcessView, processnum, processcmd, processstatus, processtime );
00149                     if ( processnum == selectedpid )
00150                     {
00151                         selecteditem = newitem;
00152                     }
00153                 }
00154             }
00155         }
00156         ProcessView->setCurrentItem( selecteditem );
00157     }
00158 
00159     delete proclist;
00160     delete procdir;
00161 }
00162 
00163 void ProcessInfo::slotSendClicked()
00164 {
00165     OListViewItem *currprocess = static_cast<OListViewItem*>( ProcessView->currentItem() );
00166     if ( !currprocess )
00167     {
00168         return;
00169     }
00170 
00171     QString capstr = tr( "Really want to send %1\nto this process?" ).arg( SignalCB->currentText() );
00172 
00173 
00174     if ( QMessageBox::warning( this, currprocess->text( 1 ), capstr,
00175                                QMessageBox::Yes | QMessageBox::Default, QMessageBox::No | QMessageBox::Escape ) == QMessageBox::Yes )
00176     {
00177         currprocess = static_cast<OListViewItem*>( ProcessView->currentItem() );
00178         if ( currprocess )
00179         {
00180             QString sigstr = SignalCB->currentText();
00181             sigstr.truncate(2);
00182             int sigid = sigstr.toUInt();
00183             kill( currprocess->text( 0 ).stripWhiteSpace().toUInt(), sigid );
00184         }
00185     }
00186 
00187 }
00188 
00189 void ProcessInfo::viewProcess( QListViewItem* process ) {
00190     if ( !process )
00191         return;
00192     viewProcess( static_cast<OListViewItem*>( process ) );
00193 }
00194 
00195 void ProcessInfo::viewProcess( OListViewItem *process )
00196 {
00197     QString pid= process->text( 0 ).stripWhiteSpace();
00198     QString command = process->text( 1 );
00199     ProcessDtl->setCaption( pid + " - " + command );
00200     FILE *statfile = fopen( ( QString ) ( "/proc/" + pid + "/status"), "r");
00201     if ( statfile )
00202     {
00203         char line[81];
00204         fgets( line, 81, statfile );
00205         ProcessDtl->detailView->setText( line );
00206         while ( fgets( line, 81, statfile ) )
00207         {
00208             ProcessDtl->detailView->append( line );
00209         }
00210         fclose( statfile );
00211     }
00212     QPEApplication::showWidget( ProcessDtl );
00213 }

Generated on Sat Nov 5 16:17:58 2005 for OPIE by  doxygen 1.4.2