00001 
00002 
00003 
00004 
00005 
00006 
00007 
00008 
00009 
00010 
00011 
00012 
00013 
00014 
00015 
00016 
00017 
00018 
00019 
00020 
00027 #include "inspectorj/toolset/classtoolset.h"
00028 #include <iostream>
00029 
00030 namespace inspectorj {
00031 namespace toolset {
00032 
00033 using inspectorj::model::ClassTableModel;
00034 using inspectorj::model::ClassTreeModel;
00035 using inspectorj::model::JavaClass;
00036 using inspectorj::jdwp::JDWPCommand;
00037 using inspectorj::client::ConnectionManager;
00038 
00045 ClassToolSet::ClassToolSet(ConnectionManager& connectionManager, SessionProfile** prof)
00046     : connection(connectionManager), profile(prof)
00047 {
00048     classTreeModel = new ClassTreeModel(this);    
00049     classTableModel = new ClassTableModel(classes, profile);
00050     createActions();
00051     setupConnections();
00052 }
00053 
00057 void ClassToolSet::createActions()
00058 {
00059     tableModelAction = new JDWPAction(this);
00060     byteCodesAction = new JDWPAction(this);
00061     updateClassFieldsAction = new JDWPAction(this);
00062     updateClassMethodsAction = new JDWPAction(this);    
00063 }
00064 
00068 void ClassToolSet::setupConnections()
00069 {
00070     connect(tableModelAction, SIGNAL(triggered(JDWPPacket&)), classTableModel, SLOT (initModel(JDWPPacket&)));
00071     connect(tableModelAction, SIGNAL(finished()), this, SIGNAL(tableModelReady()));
00072     connect(byteCodesAction, SIGNAL (triggered(JDWPPacket&)), this, SLOT (getBytecodeString(JDWPPacket&)));    
00073 }
00074 
00078 ClassToolSet::~ClassToolSet()
00079 {       
00080     delete classTableModel;
00081     classTableModel = 0;
00082     
00083     delete tableModelAction;
00084     tableModelAction = 0;
00085 }
00086 
00090 void ClassToolSet::getAllLoadedClasses()
00091 {
00092     qDeleteAll(classes);
00093     classes.clear();
00094     classMap.clear();
00095     JDWPCommand *cmd = JDWPCommand::newCommand(VM_CMD_ALL_CLASSES);
00096     connection.sendRequest(cmd, tableModelAction);
00097 }
00098 
00102 void ClassToolSet::getClassDetails(const QModelIndex& index)
00103 {   
00104     classTreeModel->setJavaClass(classes[index.row()]);
00105     
00106     
00107     classMap.insert(classes[index.row()]->getRefTypeId().value, classes[index.row()]);
00108                                 
00109     
00110     disconnect(updateClassFieldsAction, SIGNAL (triggered(JDWPPacket&)), 0, 0);
00111     disconnect(updateClassMethodsAction, SIGNAL (triggered(JDWPPacket&)), 0, 0);
00112     
00113     connect(updateClassMethodsAction, SIGNAL (triggered(JDWPPacket&)),
00114             classes[index.row()] , SLOT(setMethods(JDWPPacket&)));
00115     connect(updateClassFieldsAction,  SIGNAL (triggered(JDWPPacket&)),
00116             classes[index.row()] , SLOT(setFields(JDWPPacket&)));
00117     connect(classes[index.row()], SIGNAL (initialized()), this, SIGNAL (treeModelReady()));
00118         
00119     
00120     if (classes[index.row()]->isInitialized()) {
00121         emit treeModelReady();
00122         return;
00123     }
00124     
00125     
00126     if (! classes[index.row()]->isFieldsSet()) {
00127         JDWPCommand *fieldsCmd = JDWPCommand::newCommand(REF_TYPE_CMD_FIELDS);
00128         *fieldsCmd << classes[index.row()]->getRefTypeId();
00129         connection.sendRequest(fieldsCmd, updateClassFieldsAction);
00130     }
00131     
00132     if (! classes[index.row()]->isMethodsSet()) {    
00133         JDWPCommand *methodsCmd = JDWPCommand::newCommand(REF_TYPE_CMD_METHODS);
00134         *methodsCmd << classes[index.row()]->getRefTypeId();
00135         connection.sendRequest(methodsCmd, updateClassMethodsAction);
00136     }
00137 }
00138 
00142 ClassTableModel* ClassToolSet::getClassTableModel()
00143 {
00144     return classTableModel;
00145 }
00146 
00150 ClassTreeModel* ClassToolSet::getClassTreeModel()
00151 {
00152     return classTreeModel;
00153 }
00154 
00164 void ClassToolSet::disassembleBytecodes(const QModelIndex &index, bool disassemble,
00165                                 bool lineNumbers, bool fld, bool internal, bool verbose)
00166 {
00167     
00168     javapOutput.clear();
00169 
00170     
00171     ReferenceTypeID refid = classes[index.row()]->getRefTypeId();
00172     
00173     
00174     QString options;
00175     if (disassemble)
00176         options.append("d");
00177     if (lineNumbers)
00178         options.append("l");
00179     if (fld)
00180         options.append("f");
00181     if (internal)
00182         options.append("i");
00183     if (verbose)
00184         options.append("v");
00185     
00186     if (options.length() < 5) {
00187         options.resize(5);
00188     }
00189     
00190     if(connection.isAttached()) {
00191         JDWPCommand *cmd = JDWPCommand::newCommand(BC_TYPE_CMD_DISASSEMBLE); 
00192         *cmd << refid << options;           
00193         connection.sendRequest(cmd,  byteCodesAction);
00194     }
00195 }
00196 
00197 void ClassToolSet::prepareBytecodeOutput(QTextDocument *doc)
00198 {
00199     doc->setPlainText(javapOutput);
00200 }
00201 
00202 void ClassToolSet::getBytecodeString(JDWPPacket& packet)
00203 {
00204     if (packet.getErrorCode() != ERR_NONE) {
00205         QString err;
00206         connection.getJDWPError(packet.getErrorCode(), err);
00207        javapOutput.append("Bytecode generation failed:").append("\n");
00208        javapOutput.append(err).append("\n");
00209     } else {
00210         packet >> javapOutput;
00211     }
00212     emit bytecodesReady();
00213 }
00214 
00215 
00216 } 
00217 } 
00218