e0e19ccbe6064fc1dbfae9a1ee7d2e1c9ceee023
[phpeclipse.git] / net.sourceforge.phpeclipse.debug.core / src / net / sourceforge / phpdt / internal / debug / core / PHPDBGInterface.java
1 /**********************************************************************
2 Copyright (c) 2000, 2002 IBM Corp. and others.
3 All rights reserved. This program and the accompanying materials
4 are made available under the terms of the Common Public License v1.0
5 which accompanies this distribution, and is available at
6 http://www.eclipse.org/legal/cpl-v10.html
7
8 Contributors:
9         Vicente Fernando - www.alfersoft.com.ar - Initial implementation
10         Christian Perkonig - remote debug
11 **********************************************************************/
12 package net.sourceforge.phpdt.internal.debug.core;
13
14 import java.io.IOException;
15 import java.io.BufferedReader;
16 import java.io.OutputStream;
17 import java.util.Vector;
18
19 import org.eclipse.core.runtime.IStatus;
20 import org.eclipse.core.runtime.Status;
21 import org.eclipse.debug.core.DebugException;
22
23 import net.sourceforge.phpdt.internal.debug.core.model.PHPStackFrame;
24 import net.sourceforge.phpdt.internal.debug.core.model.PHPVariable;
25 import net.sourceforge.phpdt.internal.debug.core.model.PHPDBGEvalString;
26
27 public class PHPDBGInterface {
28
29         // Public
30         public boolean sessionEnded= false;
31         public int sessType= -1;        
32         public int BPUnderHit= 0;
33         public String sessID= new String();
34         
35         // Private
36         private int[] LastBPRead= new int[10];
37         private Vector DBGBPList= new Vector();
38         private PHPStackFrame[] DBGStackList;
39         private PHPVariable[] DBGVariableList;
40         private Vector DBGMods= new Vector();
41         private BufferedReader in;
42         private OutputStream os;
43         private boolean shouldStop= false;
44         private String evalRet= new String("");
45         private String serGlobals= new String("");
46         private int rawCounter=1000;
47         private PHPDBGProxy proxy= null;
48
49         private int lastCmd=-1;
50         private int sid=0;
51         private boolean stopOnError= false;
52         private char[] lastCommand= new char[4];
53          
54         public PHPDBGInterface(BufferedReader in, OutputStream os, PHPDBGProxy proxy) {
55                 DBGBPList.clear();
56                 this.in= in;
57                 this.os= os;
58                 this.proxy= proxy;
59         }
60
61         public int addBreakpoint(String mod_name, int line) throws IOException {
62                 return setBreakpoint(mod_name, "", line, PHPDBGBase.BPS_ENABLED + PHPDBGBase.BPS_UNRESOLVED, 0, 0, 0, 0, 0);
63         }
64
65         public void removeBreakpoint(String mod_name, int line, int bpNo) throws IOException {
66                 setBreakpoint(mod_name, "", line, PHPDBGBase.BPS_DISABLED, 0, 0, 0, bpNo, 0);
67         }
68
69         public void requestDBGVersion() throws IOException {
70                 PHPDBGPacket DBGPacket= new PHPDBGPacket(PHPDBGBase.DBGA_REQUEST);
71                 PHPDBGFrame DBGFrame= new PHPDBGFrame(PHPDBGBase.FRAME_VER);
72                 
73                 DBGPacket.addFrame(DBGFrame);
74
75                 if(proxy.getSocket().isClosed()) return;
76                 DBGPacket.sendPacket(os);
77         }
78
79         public void getSourceTree() throws IOException {
80                 PHPDBGPacket DBGPacket= new PHPDBGPacket(PHPDBGBase.DBGA_REQUEST);
81                 PHPDBGFrame DBGFrame= new PHPDBGFrame(PHPDBGBase.FRAME_SRC_TREE);
82                 
83                 DBGPacket.addFrame(DBGFrame);
84                 
85                 if(proxy.getSocket().isClosed()) return;
86                 DBGPacket.sendPacket(os);
87
88                 // Wait response (1 second) and read response
89                 waitResponse(1000);
90                 flushAllPackets();
91         }
92
93         public void addDBGModName(String modName) throws IOException {
94                 PHPDBGPacket DBGPacket= new PHPDBGPacket(PHPDBGBase.DBGA_REQUEST);
95                 PHPDBGFrame DBGFrame= new PHPDBGFrame(PHPDBGBase.FRAME_RAWDATA);
96                 
97                 rawCounter++;
98                 DBGFrame.addInt(rawCounter);                            // FRAME_RAWDATA ID
99                 DBGFrame.addInt(modName.length() + 1);          // length of rawdata (+ null char)
100                 DBGFrame.addString(modName);                            // file name
101                 DBGFrame.addChar('\0');                                         // null char
102
103                 DBGPacket.addFrame(DBGFrame);
104                 
105                 if(proxy.getSocket().isClosed()) return;
106                 DBGPacket.sendPacket(os);
107         }
108
109         // Returns DBG Breakpoint ID
110         private int setBreakpoint(String mod_name, String condition, int line, int state, int istemp, int hitcount, int skiphits, int bpno, int isunderhit) throws IOException {
111                 int modNo= 0;
112
113                 PHPDBGPacket DBGPacket= new PHPDBGPacket(PHPDBGBase.DBGA_REQUEST);
114                 PHPDBGFrame DBGFrame1= new PHPDBGFrame(PHPDBGBase.FRAME_BPS);
115                 PHPDBGFrame DBGFrame2= new PHPDBGFrame(PHPDBGBase.FRAME_RAWDATA);
116
117                 modNo= getModByName(mod_name);
118                 
119                 if(modNo >= 0) {
120                         DBGFrame1.addInt(modNo);        // mod number
121                 } else {
122                         DBGFrame1.addInt(0);            // mod number (0 use file name)
123                 }
124                 
125                 DBGFrame1.addInt(line);                 // line number
126                 
127                 if(modNo >= 0) {
128                         DBGFrame1.addInt(0);                    // use mod number
129                 } else {
130                         rawCounter++;
131                         DBGFrame1.addInt(rawCounter);   // ID of FRAME_RAWDATA to send file name
132                 }
133
134                 DBGFrame1.addInt(state);                // state BPS_*
135                 DBGFrame1.addInt(istemp);               // istemp
136                 DBGFrame1.addInt(hitcount);             // hit count
137                 DBGFrame1.addInt(skiphits);             // skip hits
138                 DBGFrame1.addInt(0);                    // ID of condition
139                 DBGFrame1.addInt(bpno);                 // breakpoint number
140                 DBGFrame1.addInt(isunderhit);   // is under hit
141                 
142                 if(modNo < 0) {
143                         DBGFrame2.addInt(rawCounter);                           // FRAME_RAWDATA ID
144                         DBGFrame2.addInt(mod_name.length() + 1);        // length of rawdata (+ null char)
145                         DBGFrame2.addString(mod_name);                          // file name
146                         DBGFrame2.addChar('\0');                                        // null char
147                         // First add file name data
148                         DBGPacket.addFrame(DBGFrame2);
149                 }
150
151                 // Second add command data
152                 DBGPacket.addFrame(DBGFrame1);
153
154                 if(proxy.getSocket().isClosed()) return 0;
155                 DBGPacket.sendPacket(os);
156
157                 clearLastBP();
158
159                 // Wait response (1 second) and read response
160                 waitResponse(1000);
161                 flushAllPackets();
162
163                 return LastBPRead[8];
164         }
165
166         private void clearLastBP() {
167                 int i;
168
169                 for(i=0; i < LastBPRead.length; i++)
170                         LastBPRead[i]= 0;
171         }
172
173         private void copyToLastBP(int[] BPBody) {
174                 int i;
175
176                 for(i=0; i < LastBPRead.length; i++)
177                         LastBPRead[i]= BPBody[i];
178         }
179
180         public void continueExecution() throws IOException {
181                 BPUnderHit= 0;
182                 PHPDBGPacket DBGPacket= new PHPDBGPacket(PHPDBGBase.DBGA_CONTINUE);
183                 if(proxy.getSocket().isClosed()) return;
184                 DBGPacket.sendPacket(os);
185                 lastCommand= PHPDBGBase.DBGA_CONTINUE;
186         }
187
188         public void pauseExecution() throws IOException {
189                 PHPDBGPacket DBGPacket= new PHPDBGPacket(PHPDBGBase.IntToChar4(PHPDBGBase.DBGC_PAUSE));
190                 if(proxy.getSocket().isClosed()) return;
191                 DBGPacket.sendPacket(os);
192         }
193
194         private int getBPUnderHit() {
195                 int i, BPUnder=0;
196                 int[] dbg_bpl_body= new int[10];
197
198                 // look for bp under hit
199                 for(i=0; i < DBGBPList.size(); i++) {
200                         dbg_bpl_body= (int[]) DBGBPList.get(i);
201                         if(dbg_bpl_body[9] == 1) {
202                                 BPUnder= dbg_bpl_body[8];
203                         }
204                 }
205                 return BPUnder;
206         }
207         
208         public int getLastCmd()
209         {
210                 return lastCmd;
211         }
212         
213         public int getSID()
214         {
215           return sid;
216   }
217         
218         public void setLastCmd(int cmd)
219         {
220                 lastCmd=cmd;
221         }
222
223         public void stepInto() throws IOException {
224                 BPUnderHit= 0;
225                 PHPDBGPacket DBGPacket= new PHPDBGPacket(PHPDBGBase.DBGA_STEPINTO);
226                 if(proxy.getSocket().isClosed()) return;
227                 DBGPacket.sendPacket(os);
228                 lastCommand= PHPDBGBase.DBGA_STEPINTO;
229         }
230
231         public void stepOver() throws IOException {
232                 BPUnderHit= 0;
233                 PHPDBGPacket DBGPacket= new PHPDBGPacket(PHPDBGBase.DBGA_STEPOVER);
234                 if(proxy.getSocket().isClosed()) return;
235                 DBGPacket.sendPacket(os);
236                 lastCommand= PHPDBGBase.DBGA_STEPOVER;
237         }
238
239         public void stepOut() throws IOException {
240                 BPUnderHit= 0;
241                 PHPDBGPacket DBGPacket= new PHPDBGPacket(PHPDBGBase.DBGA_STEPOUT);
242                 if(proxy.getSocket().isClosed()) return;
243                 DBGPacket.sendPacket(os);
244                 lastCommand= PHPDBGBase.DBGA_STEPOUT;
245         }
246
247         public void stopExecution() throws IOException {
248                 BPUnderHit= 0;
249                 PHPDBGPacket DBGPacket= new PHPDBGPacket(PHPDBGBase.DBGA_STOP);
250                 if(proxy.getSocket().isClosed()) return;
251                 DBGPacket.sendPacket(os);
252         }
253
254         public PHPVariable[] getVariables(PHPStackFrame stack) throws IOException, DebugException  {
255                 PHPDBGPacket DBGPacket= new PHPDBGPacket(PHPDBGBase.DBGA_REQUEST);
256                 PHPDBGFrame DBGFrame1= new PHPDBGFrame(PHPDBGBase.FRAME_EVAL);
257         
258                 DBGFrame1.addInt(0);                                            // istr = raw data ID
259                 DBGFrame1.addInt(1);                                            // scope_id = -1 means current location, 0 never used, +1 first depth
260                 
261                 // Add command data
262                 DBGPacket.addFrame(DBGFrame1);
263                 
264                 if(proxy.getSocket().isClosed()) return null;
265                 DBGPacket.sendPacket(os);
266
267                 waitResponse(1000);
268                 flushAllPackets();
269                 
270                 // Process serialized variables
271                 PHPDBGEvalString evalStr=new PHPDBGEvalString(stack,serGlobals);
272                 
273                 DBGVariableList= evalStr.getVars();
274
275                 return DBGVariableList;
276         }
277
278         public void log(String logString) throws IOException, DebugException  {
279                 PHPDBGPacket DBGPacket= new PHPDBGPacket(PHPDBGBase.DBGA_REQUEST);
280                 PHPDBGFrame DBGFrame1= new PHPDBGFrame(PHPDBGBase.FRAME_LOG);
281                 PHPDBGFrame DBGFrame2= new PHPDBGFrame(PHPDBGBase.FRAME_RAWDATA);
282
283                 rawCounter++;
284                 DBGFrame1.addInt(rawCounter);                           // ilog
285                 DBGFrame1.addInt(1);                                            // type
286                 DBGFrame1.addInt(0);                                            // mod_no
287                 DBGFrame1.addInt(0);                                            // line_no
288                 DBGFrame1.addInt(0);                                            // imod_name
289                 DBGFrame1.addInt(0);                                            // ext_info             
290
291                 DBGFrame2.addInt(rawCounter);                           // FRAME_RAWDATA ID
292                 DBGFrame2.addInt(logString.length() + 1);       // length of rawdata (+ null char)
293                 DBGFrame2.addString(logString);                         // log string
294                 DBGFrame2.addChar('\0');                                        // null char
295
296                 // Add raw data first
297                 DBGPacket.addFrame(DBGFrame2);
298                 // Add command data
299                 DBGPacket.addFrame(DBGFrame1);
300                 
301                 if(proxy.getSocket().isClosed()) return;
302                 DBGPacket.sendPacket(os);
303
304                 waitResponse(1000);
305                 flushAllPackets();
306         }
307
308         public PHPVariable[] evalBlock(PHPStackFrame stack, String evalString) throws IOException, DebugException  {
309                 PHPDBGPacket DBGPacket= new PHPDBGPacket(PHPDBGBase.DBGA_REQUEST);
310                 PHPDBGFrame DBGFrame1= new PHPDBGFrame(PHPDBGBase.FRAME_EVAL);
311                 PHPDBGFrame DBGFrame2= new PHPDBGFrame(PHPDBGBase.FRAME_RAWDATA);
312
313                 rawCounter++;
314                 DBGFrame1.addInt(rawCounter);                           // istr = raw data ID
315                 DBGFrame1.addInt(1);                                            // scope_id = -1 means current location, 0 never used, +1 first depth
316
317                 DBGFrame2.addInt(rawCounter);                           // FRAME_RAWDATA ID
318                 DBGFrame2.addInt(evalString.length() + 1);      // length of rawdata (+ null char)
319                 DBGFrame2.addString(evalString);                        // eval block
320                 DBGFrame2.addChar('\0');                                        // null char
321
322                 // Add raw data first
323                 DBGPacket.addFrame(DBGFrame2);
324                 // Add command data
325                 DBGPacket.addFrame(DBGFrame1);
326                 
327                 if(proxy.getSocket().isClosed()) return null;
328                 DBGPacket.sendPacket(os);
329
330                 waitResponse(1000);
331                 flushAllPackets();
332                 
333                 PHPDBGEvalString evalStr=new PHPDBGEvalString(stack,evalRet);
334                 
335                 return evalStr.getVars();
336                 
337         }
338
339         public void flushAllPackets() throws IOException {
340                 while(readResponse() != 0);
341         }
342
343         public String getModByNo(int modNo) {
344                 int i;
345                 PHPDBGMod dbg_mod;
346
347                 // look for mod
348                 for(i=0; i < DBGMods.size(); i++) {
349                         dbg_mod= (PHPDBGMod) DBGMods.get(i);
350                         if(dbg_mod.getNo() == modNo) {
351                                 return dbg_mod.getName(); 
352                         }
353                 }
354                 return "";
355         }
356
357         private int getModByName(String modName) {
358                 int i;
359                 PHPDBGMod dbg_mod;
360
361                 // look for mod
362                 for(i=0; i < DBGMods.size(); i++) {
363                         dbg_mod= (PHPDBGMod) DBGMods.get(i);
364                         if(dbg_mod.getName().equalsIgnoreCase(modName)) {
365                                 return dbg_mod.getNo(); 
366                         }
367                 }
368                 return -1;
369         }
370
371         private String getRawFrameData(char[] framesInfo, int frameNo) {
372                 int nextFrame= 0;
373                 int[] dbg_frame= new int[2];
374                 
375                 while(nextFrame < framesInfo.length) {
376                         dbg_frame[0] = PHPDBGBase.Char4ToInt(framesInfo, nextFrame);            // frame name
377                         dbg_frame[1] = PHPDBGBase.Char4ToInt(framesInfo, nextFrame + 4);        // frame size
378
379                         nextFrame += 8;
380                         if(dbg_frame[1] == 0) return "";
381
382                         switch(dbg_frame[0]) {
383                                 case PHPDBGBase.FRAME_RAWDATA:
384                                         if(frameNo == PHPDBGBase.Char4ToInt(framesInfo, nextFrame)) {
385                                                 int toRead= PHPDBGBase.Char4ToInt(framesInfo, nextFrame + 4);
386                                                 return String.copyValueOf(framesInfo, nextFrame + 8, toRead);
387                                         }
388                                         break;
389                         }
390                         // go to next frame
391                         nextFrame += dbg_frame[1];
392                 }
393                 return "";
394         }
395
396
397         public int readResponse() throws IOException {
398                 int bytesToRead=0, nextFrame=0, i=0, cmdReceived=0, stackIndex=0;
399                 boolean errorStack= false;
400                 char[] dbg_header_struct_read= new char[16];
401                 int[] dbg_header_struct= new int[4];
402                 int[] dbg_bpl_tmp= new int[10];
403                 int[] dbg_frame= new int[2];
404                 int[] dbg_eval_tmp= new int[3];
405                 int[] dbg_src_tree_tmp= new int[4];
406                 int[] dbg_error_tmp= new int[2];
407                 Vector rawList= new Vector();
408                 Vector stackList= new Vector();
409                 PHPStackFrame[] newStackList;
410                 
411                 rawList.clear();
412                 stackList.clear();
413                 // Read from input
414                 while(readInput(dbg_header_struct_read, 16) != 0) {
415                         dbg_header_struct[0] = PHPDBGBase.Char4ToInt(dbg_header_struct_read, 0);
416                         dbg_header_struct[1] = PHPDBGBase.Char4ToInt(dbg_header_struct_read, 4);
417                         dbg_header_struct[2] = PHPDBGBase.Char4ToInt(dbg_header_struct_read, 8);
418                         dbg_header_struct[3] = PHPDBGBase.Char4ToInt(dbg_header_struct_read, 12);
419                         
420                         // Check DBG sync bytes
421                         if(dbg_header_struct[0] != 0x5953) return 0;
422                         
423                         cmdReceived= dbg_header_struct[1];
424                         setLastCmd(cmdReceived);
425                         bytesToRead= dbg_header_struct[3];
426
427                         //System.out.println("Response Received: " + cmdReceived);
428                         char[] entirePack= new char[bytesToRead];
429
430                         if(bytesToRead > 0) {
431                                 if(readInput(entirePack, bytesToRead) < bytesToRead) return 0;
432                         }
433                         
434                         // First process frames
435                         nextFrame= 0;
436                         while(nextFrame < bytesToRead) {
437                                 dbg_frame[0] = PHPDBGBase.Char4ToInt(entirePack, nextFrame);            // frame name
438                                 dbg_frame[1] = PHPDBGBase.Char4ToInt(entirePack, nextFrame + 4);        // frame size
439                                 nextFrame += 8;
440                                 if(dbg_frame[1] == 0) return 0;
441                                 switch(dbg_frame[0]) {
442                                         case PHPDBGBase.FRAME_STACK:
443                                                 int[] dbg_stack_new= new int[4];
444                                                 dbg_stack_new[0] = PHPDBGBase.Char4ToInt(entirePack, nextFrame + 0);    // line no
445                                                 dbg_stack_new[1] = PHPDBGBase.Char4ToInt(entirePack, nextFrame + 4);    // mod no
446                                                 dbg_stack_new[2] = PHPDBGBase.Char4ToInt(entirePack, nextFrame + 8);    // scope id
447                                                 dbg_stack_new[3] = PHPDBGBase.Char4ToInt(entirePack, nextFrame + 12);   // id of description string
448
449                                                 if(dbg_stack_new[1] != 0 && !errorStack) {
450                                                         stackIndex++;
451                                                         PHPStackFrame newStack= new PHPStackFrame(null, getModByNo(dbg_stack_new[1]), dbg_stack_new[0], stackIndex, getRawFrameData(entirePack, dbg_stack_new[3]), dbg_stack_new[1]);
452                                                         stackList.add(newStack);
453                                                 }
454                                                 errorStack= false;
455                                                 break;
456                                         case PHPDBGBase.FRAME_SOURCE:
457                                                 break;
458                                         case PHPDBGBase.FRAME_SRC_TREE:
459                                                 dbg_src_tree_tmp[0] = PHPDBGBase.Char4ToInt(entirePack, nextFrame + 0);         // parent_mod_no
460                                                 dbg_src_tree_tmp[1] = PHPDBGBase.Char4ToInt(entirePack, nextFrame + 4);         // parent_line_no               /* NOT USED */
461                                                 dbg_src_tree_tmp[2] = PHPDBGBase.Char4ToInt(entirePack, nextFrame + 8);         // mod_no
462                                                 dbg_src_tree_tmp[3] = PHPDBGBase.Char4ToInt(entirePack, nextFrame + 12);        // imod_name
463
464                                                 if(getModByNo(dbg_src_tree_tmp[2]).equals("")) {
465                                                         String fileName= new String(getRawFrameData(entirePack, dbg_src_tree_tmp[3]));
466                                                         // Remove '\0' char
467                                                         if(fileName.length() > 0) fileName= fileName.substring(0, fileName.length() - 1);
468
469                                                         if(dbg_src_tree_tmp[2] != 0) {
470                                                                 PHPDBGMod modNew= new PHPDBGMod(dbg_src_tree_tmp[2], fileName);
471                                                                 DBGMods.add(modNew);
472                                                         }
473                                                 }
474                                                 break;
475                                         case PHPDBGBase.FRAME_RAWDATA:
476                                                 break;
477                                         case PHPDBGBase.FRAME_ERROR:
478                                                 errorStack= true;
479                                                 dbg_error_tmp[0] = PHPDBGBase.Char4ToInt(entirePack, nextFrame + 0);            // type                 /* type of error */
480                                                 dbg_error_tmp[1] = PHPDBGBase.Char4ToInt(entirePack, nextFrame + 4);            // imessage             /* ID of error message */
481                                                 
482                                                 String error= "\n";
483                                                 switch(dbg_error_tmp[0]) {
484                                                         case PHPDBGBase.E_ERROR:
485                                                                 error+= "[Error]";
486                                                                 break;
487                                                         case PHPDBGBase.E_WARNING:
488                                                                 error+= "[Warning]";
489                                                                 break;
490                                                         case PHPDBGBase.E_PARSE:
491                                                                 error+= "[Parse Error]";
492                                                                 break;
493                                                         case PHPDBGBase.E_NOTICE:
494                                                                 error+= "[Notice]";
495                                                                 break;
496                                                         case PHPDBGBase.E_CORE_ERROR:
497                                                                 error+= "[Core Error]";
498                                                                 break;
499                                                         case PHPDBGBase.E_CORE_WARNING:
500                                                                 error+= "[Core Warning]";
501                                                                 break;
502                                                         case PHPDBGBase.E_COMPILE_ERROR:
503                                                                 error+= "[Compile Error]";
504                                                                 break;
505                                                         case PHPDBGBase.E_COMPILE_WARNING:
506                                                                 error+= "[Compile Warning]";
507                                                                 break;
508                                                         case PHPDBGBase.E_USER_ERROR:
509                                                                 error+= "[User Error]";
510                                                                 break;
511                                                         case PHPDBGBase.E_USER_WARNING:
512                                                                 error+= "[User Warning]";
513                                                                 break;
514                                                         case PHPDBGBase.E_USER_NOTICE:
515                                                                 error+= "[User Notice]";
516                                                                 break;
517                                                         default:
518                                                                 error+= "[Unexpected Error]";
519                                                                 break;
520                                                 }
521                                                 error+= ": ";
522                                                 error+= new String(getRawFrameData(entirePack, dbg_error_tmp[1]));
523                                                 // Remove '\0' char
524                                                 if(error.length() > 0) error= error.substring(0, error.length() - 1);
525                                                 error+= "\n";
526
527                                                 PHPDebugCorePlugin.log(new DebugException(new Status(IStatus.WARNING, PHPDebugCorePlugin.PLUGIN_ID, IStatus.OK, error, null)));
528                                                 // To print errors on the console, I must execute a code in the
529                                                 // php context, that write the stderr... I didn't found a better way
530                                                 // TODO: Find a better way????
531                                                 String codeExec= "";
532                                                 codeExec= "fwrite(fopen('php://stderr', 'w'),\\\"" + error + "\\\");";
533 //                                              try {
534 //                                                      evalBlock("eval(\"" + codeExec + "\");");
535 //                                              } catch (DebugException e) {
536 //                                                      PHPDebugCorePlugin.log(e);
537 //                                              }
538                                                 if(!stopOnError) {
539                                                         if(lastCommand.equals(PHPDBGBase.DBGA_CONTINUE)) {
540                                                                 continueExecution();
541                                                         } else if(lastCommand.equals(PHPDBGBase.DBGA_STEPINTO)) {
542                                                                 stepInto();
543                                                         } else if(lastCommand.equals(PHPDBGBase.DBGA_STEPOUT)) {
544                                                                 stepOut();
545                                                         } else if(lastCommand.equals(PHPDBGBase.DBGA_STEPOVER)) {
546                                                                 stepOver();
547                                                         }
548                                                 }
549                                                 break;
550                                         case PHPDBGBase.FRAME_EVAL:
551                                                 String evalString= new String("");
552                                                 dbg_eval_tmp[0] = PHPDBGBase.Char4ToInt(entirePack, nextFrame + 0); // istr
553                                                 dbg_eval_tmp[1] = PHPDBGBase.Char4ToInt(entirePack, nextFrame + 4); // iresult
554                                                 dbg_eval_tmp[2] = PHPDBGBase.Char4ToInt(entirePack, nextFrame + 8); // ierror
555
556                                                 evalRet= getRawFrameData(entirePack, dbg_eval_tmp[1]);
557                                                 evalString= getRawFrameData(entirePack, dbg_eval_tmp[0]);
558                                                 serGlobals= evalRet;
559                                                 break;
560                                         case PHPDBGBase.FRAME_BPS:
561                                                 break;
562                                         case PHPDBGBase.FRAME_BPL:
563                                                 int[] dbg_bpl_new= new int[10];
564                                                 dbg_bpl_new[0] = PHPDBGBase.Char4ToInt(entirePack, nextFrame + 0);
565                                                 dbg_bpl_new[1] = PHPDBGBase.Char4ToInt(entirePack, nextFrame + 4);
566                                                 dbg_bpl_new[2] = PHPDBGBase.Char4ToInt(entirePack, nextFrame + 8);
567                                                 dbg_bpl_new[3] = PHPDBGBase.Char4ToInt(entirePack, nextFrame + 12);
568                                                 dbg_bpl_new[4] = PHPDBGBase.Char4ToInt(entirePack, nextFrame + 16);
569                                                 dbg_bpl_new[5] = PHPDBGBase.Char4ToInt(entirePack, nextFrame + 20);
570                                                 dbg_bpl_new[6] = PHPDBGBase.Char4ToInt(entirePack, nextFrame + 24);
571                                                 dbg_bpl_new[7] = PHPDBGBase.Char4ToInt(entirePack, nextFrame + 28);
572                                                 dbg_bpl_new[8] = PHPDBGBase.Char4ToInt(entirePack, nextFrame + 32);
573                                                 dbg_bpl_new[9] = PHPDBGBase.Char4ToInt(entirePack, nextFrame + 36);
574         
575                                                 // look if breakpoint already exists in vector
576                                                 for(i=0; i < DBGBPList.size(); i++) {
577                                                         dbg_bpl_tmp= (int[]) DBGBPList.get(i);
578                                                         if(dbg_bpl_tmp[8] == dbg_bpl_new[8]) {
579                                                                 DBGBPList.remove(i);
580                                                                 break;
581                                                         }
582                                                 }
583
584                                                 // add breakpoint to vector
585                                                 DBGBPList.add(dbg_bpl_new);
586                                                 copyToLastBP(dbg_bpl_new);
587                                                 
588                                                 // mod no returned?
589                                                 if(getModByNo(dbg_bpl_new[0]).equals("")) {
590                                                         String fileName= new String(getRawFrameData(entirePack, dbg_bpl_new[2]));
591                                                         // Remove '\0' char
592                                                         if(fileName.length() > 0) fileName= fileName.substring(0, fileName.length() - 1);
593                                                         if(dbg_bpl_new[0] != 0) {
594                                                                 PHPDBGMod modNew= new PHPDBGMod(dbg_bpl_new[0], fileName);
595                                                                 DBGMods.add(modNew);
596                                                         }
597                                                 }                                                       
598                                                 break;
599                                         case PHPDBGBase.FRAME_VER:
600                                                 break;
601                                         case PHPDBGBase.FRAME_SID:
602                                           sid = PHPDBGBase.Char4ToInt(entirePack, nextFrame + 0);
603                                                 break;
604                                         case PHPDBGBase.FRAME_SRCLINESINFO:
605                                                 break;
606                                         case PHPDBGBase.FRAME_SRCCTXINFO:
607                                                 break;
608                                         case PHPDBGBase.FRAME_LOG:
609                                                 break;
610                                         case PHPDBGBase.FRAME_PROF:
611                                                 break;
612                                         case PHPDBGBase.FRAME_PROF_C:
613                                                 break;
614                                         case PHPDBGBase.FRAME_SET_OPT:
615                                                 break;
616                                 }
617                                 // go to next frame
618                                 nextFrame += dbg_frame[1];
619                         }
620                         
621                         // Now process command
622                         switch(cmdReceived) {
623                                 case PHPDBGBase.DBGC_REPLY:
624                                         break;
625                                 case PHPDBGBase.DBGC_STARTUP:
626                                         break;
627                                 case PHPDBGBase.DBGC_END:
628                                         sessionEnded= true;
629                                         break;
630                                 case PHPDBGBase.DBGC_BREAKPOINT:
631                                         newStackList= new PHPStackFrame[stackList.size()];
632                                         newStackList= (PHPStackFrame[]) stackList.toArray(newStackList);
633                                         DBGStackList= newStackList;
634                                         BPUnderHit= getBPUnderHit();
635                                         break;
636                                 case PHPDBGBase.DBGC_STEPINTO_DONE:
637                                 case PHPDBGBase.DBGC_STEPOVER_DONE:
638                                 case PHPDBGBase.DBGC_STEPOUT_DONE:
639                                 case PHPDBGBase.DBGC_EMBEDDED_BREAK:
640                                 case PHPDBGBase.DBGC_PAUSE:
641                                         BPUnderHit= 1;
642                                         newStackList= new PHPStackFrame[stackList.size()];
643                                         newStackList= (PHPStackFrame[]) stackList.toArray(newStackList);
644                                         DBGStackList= newStackList;
645                                         break;
646                                 case PHPDBGBase.DBGC_ERROR:
647                                         stackList.clear();
648                                         newStackList= new PHPStackFrame[stackList.size()];
649                                         newStackList= (PHPStackFrame[]) stackList.toArray(newStackList);
650                                         DBGStackList= newStackList;
651                                         break;
652                                 case PHPDBGBase.DBGC_LOG:
653                                         break;
654                                 case PHPDBGBase.DBGC_SID:
655                                         break;
656                         }
657                 }
658                 return cmdReceived;
659         }
660
661         public PHPStackFrame[] getStackList() {
662                 return DBGStackList;
663         }
664
665         private int readInput(char[] buffer, int bytes) throws IOException {
666                 int bytesRead= 0;
667
668                 for(int i=0; i < bytes; i++) {
669                         if(in.ready()) {
670                                 buffer[i]= (char) (in.read() & 0x00FF);
671                                 bytesRead++;
672                         }
673                         else
674                                 break;                          
675                 }
676                 return bytesRead;
677         }
678         
679         public void setShouldStop() {
680                 this.shouldStop= true;
681         }
682
683         public boolean waitResponse(long milliseconds) throws IOException {
684                 long timeout= System.currentTimeMillis() + milliseconds;
685                 while(System.currentTimeMillis() < timeout) {
686                         if(in.ready() || shouldStop) {
687                                 break;
688                         }
689                 }
690                 return in.ready();
691         }
692 }