266460b09c1c64f635db1f0924469ec2040e7b27
[phpeclipse.git] / net.sourceforge.phpeclipse.debug.core / bin / net / sourceforge / phpdt / internal / debug / core / .#PHPDBGInterface.java.1.3
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 import java.lang.System;
19 import org.eclipse.debug.core.DebugException;
20 import net.sourceforge.phpdt.internal.debug.core.model.PHPStackFrame;
21 import net.sourceforge.phpdt.internal.debug.core.model.PHPVariable;
22 import net.sourceforge.phpdt.internal.debug.core.model.PHPValue;
23 import net.sourceforge.phpdt.internal.debug.core.PHPDBGMod;
24
25 public class PHPDBGInterface {
26
27         // Public
28         public boolean sessionEnded= false;
29         public int sessType= -1;        
30         public int BPUnderHit= 0;
31         public String sessID= new String();
32         
33         // Private
34         private int[] LastBPRead= new int[10];
35         private Vector DBGBPList= new Vector();
36         private PHPStackFrame[] DBGStackList;
37         private PHPVariable[] DBGVariableList;
38         private Vector DBGMods= new Vector();
39         private Vector DBGVars= new Vector();
40         private BufferedReader in;
41         private OutputStream os;
42         private boolean shouldStop= false, isRef= false, hasChildren= false, isObject= false;
43         private String evalRet= new String("");
44         private String serGlobals= new String("");
45         private String typeRead= new String("");
46         private String className= new String("");
47         private int finalPos=0, refCounter=0, rawCounter=1000;
48         private PHPDBGProxy proxy= null;
49         private int lastCmd=-1;
50         private int sid=0;
51          
52         public PHPDBGInterface(BufferedReader in, OutputStream os, PHPDBGProxy proxy) {
53                 DBGBPList.clear();
54                 this.in= in;
55                 this.os= os;
56                 this.proxy= proxy;
57         }
58
59         public int addBreakpoint(String mod_name, int line) throws IOException {
60                 return setBreakpoint(mod_name, "", line, PHPDBGBase.BPS_ENABLED + PHPDBGBase.BPS_UNRESOLVED, 0, 0, 0, 0, 0);
61         }
62
63         public void removeBreakpoint(String mod_name, int line, int bpNo) throws IOException {
64                 setBreakpoint(mod_name, "", line, PHPDBGBase.BPS_DISABLED, 0, 0, 0, bpNo, 0);
65         }
66
67         public void requestDBGVersion() throws IOException {
68                 PHPDBGPacket DBGPacket= new PHPDBGPacket(PHPDBGBase.DBGA_REQUEST);
69                 PHPDBGFrame DBGFrame= new PHPDBGFrame(PHPDBGBase.FRAME_VER);
70                 
71                 DBGPacket.addFrame(DBGFrame);
72
73                 if(proxy.getSocket().isClosed()) return;
74                 DBGPacket.sendPacket(os);
75         }
76
77         public void getSourceTree() throws IOException {
78                 PHPDBGPacket DBGPacket= new PHPDBGPacket(PHPDBGBase.DBGA_REQUEST);
79                 PHPDBGFrame DBGFrame= new PHPDBGFrame(PHPDBGBase.FRAME_SRC_TREE);
80                 
81                 DBGPacket.addFrame(DBGFrame);
82                 
83                 if(proxy.getSocket().isClosed()) return;
84                 DBGPacket.sendPacket(os);
85
86                 // Wait response (1 second) and read response
87                 waitResponse(1000);
88                 flushAllPackets();
89         }
90
91         public void addDBGModName(String modName) throws IOException {
92                 PHPDBGPacket DBGPacket= new PHPDBGPacket(PHPDBGBase.DBGA_REQUEST);
93                 PHPDBGFrame DBGFrame= new PHPDBGFrame(PHPDBGBase.FRAME_RAWDATA);
94                 
95                 rawCounter++;
96                 DBGFrame.addInt(rawCounter);                            // FRAME_RAWDATA ID
97                 DBGFrame.addInt(modName.length() + 1);          // length of rawdata (+ null char)
98                 DBGFrame.addString(modName);                            // file name
99                 DBGFrame.addChar('\0');                                         // null char
100
101                 DBGPacket.addFrame(DBGFrame);
102                 
103                 if(proxy.getSocket().isClosed()) return;
104                 DBGPacket.sendPacket(os);
105         }
106
107         // Returns DBG Breakpoint ID
108         private int setBreakpoint(String mod_name, String condition, int line, int state, int istemp, int hitcount, int skiphits, int bpno, int isunderhit) throws IOException {
109                 int modNo= 0;
110
111                 PHPDBGPacket DBGPacket= new PHPDBGPacket(PHPDBGBase.DBGA_REQUEST);
112                 PHPDBGFrame DBGFrame1= new PHPDBGFrame(PHPDBGBase.FRAME_BPS);
113                 PHPDBGFrame DBGFrame2= new PHPDBGFrame(PHPDBGBase.FRAME_RAWDATA);
114
115                 modNo= getModByName(mod_name);
116                 
117                 if(modNo >= 0) {
118                         DBGFrame1.addInt(modNo);        // mod number
119                 } else {
120                         DBGFrame1.addInt(0);            // mod number (0 use file name)
121                 }
122                 
123                 DBGFrame1.addInt(line);                 // line number
124                 
125                 if(modNo >= 0) {
126                         DBGFrame1.addInt(0);                    // use mod number
127                 } else {
128                         rawCounter++;
129                         DBGFrame1.addInt(rawCounter);   // ID of FRAME_RAWDATA to send file name
130                 }
131
132                 DBGFrame1.addInt(state);                // state BPS_*
133                 DBGFrame1.addInt(istemp);               // istemp
134                 DBGFrame1.addInt(hitcount);             // hit count
135                 DBGFrame1.addInt(skiphits);             // skip hits
136                 DBGFrame1.addInt(0);                    // ID of condition
137                 DBGFrame1.addInt(bpno);                 // breakpoint number
138                 DBGFrame1.addInt(isunderhit);   // is under hit
139                 
140                 if(modNo < 0) {
141                         DBGFrame2.addInt(rawCounter);                           // FRAME_RAWDATA ID
142                         DBGFrame2.addInt(mod_name.length() + 1);        // length of rawdata (+ null char)
143                         DBGFrame2.addString(mod_name);                          // file name
144                         DBGFrame2.addChar('\0');                                        // null char
145                         // First add file name data
146                         DBGPacket.addFrame(DBGFrame2);
147                 }
148
149                 // Second add command data
150                 DBGPacket.addFrame(DBGFrame1);
151
152                 if(proxy.getSocket().isClosed()) return 0;
153                 DBGPacket.sendPacket(os);
154
155                 clearLastBP();
156
157                 // Wait response (1 second) and read response
158                 waitResponse(1000);
159                 flushAllPackets();
160
161                 return LastBPRead[8];
162         }
163
164         private void clearLastBP() {
165                 int i;
166
167                 for(i=0; i < LastBPRead.length; i++)
168                         LastBPRead[i]= 0;
169         }
170
171         private void copyToLastBP(int[] BPBody) {
172                 int i;
173
174                 for(i=0; i < LastBPRead.length; i++)
175                         LastBPRead[i]= BPBody[i];
176         }
177
178         public void continueExecution() throws IOException {
179                 BPUnderHit= 0;
180                 PHPDBGPacket DBGPacket= new PHPDBGPacket(PHPDBGBase.DBGA_CONTINUE);
181                 if(proxy.getSocket().isClosed()) return;
182                 DBGPacket.sendPacket(os);
183         }
184
185         private int getBPUnderHit() {
186                 int i, BPUnder=0;
187                 int[] dbg_bpl_body= new int[10];
188
189                 // look for bp under hit
190                 for(i=0; i < DBGBPList.size(); i++) {
191                         dbg_bpl_body= (int[]) DBGBPList.get(i);
192                         if(dbg_bpl_body[9] == 1) {
193                                 BPUnder= dbg_bpl_body[8];
194                         }
195                 }
196                 return BPUnder;
197         }
198         
199         public int getLastCmd()
200         {
201                 return lastCmd;
202         }
203         
204         public int getSID()
205         {
206           return sid;
207   }
208         
209         public void setLastCmd(int cmd)
210         {
211                 lastCmd=cmd;
212         }
213
214         public void stepInto() throws IOException {
215                 BPUnderHit= 0;
216                 PHPDBGPacket DBGPacket= new PHPDBGPacket(PHPDBGBase.DBGA_STEPINTO);
217                 if(proxy.getSocket().isClosed()) return;
218                 DBGPacket.sendPacket(os);
219         }
220
221         public void stepOver() throws IOException {
222                 BPUnderHit= 0;
223                 PHPDBGPacket DBGPacket= new PHPDBGPacket(PHPDBGBase.DBGA_STEPOVER);
224                 if(proxy.getSocket().isClosed()) return;
225                 DBGPacket.sendPacket(os);
226         }
227
228         public void stepOut() throws IOException {
229                 BPUnderHit= 0;
230                 PHPDBGPacket DBGPacket= new PHPDBGPacket(PHPDBGBase.DBGA_STEPOUT);
231                 if(proxy.getSocket().isClosed()) return;
232                 DBGPacket.sendPacket(os);
233         }
234
235         public void stopExecution() throws IOException {
236                 BPUnderHit= 0;
237                 PHPDBGPacket DBGPacket= new PHPDBGPacket(PHPDBGBase.DBGA_STOP);
238                 if(proxy.getSocket().isClosed()) return;
239                 DBGPacket.sendPacket(os);
240         }
241
242         public PHPVariable[] getVariables(PHPStackFrame stack) throws IOException, DebugException  {
243                 PHPDBGPacket DBGPacket= new PHPDBGPacket(PHPDBGBase.DBGA_REQUEST);
244                 PHPDBGFrame DBGFrame1= new PHPDBGFrame(PHPDBGBase.FRAME_EVAL);
245                 //PHPDBGFrame DBGFrame2= new PHPDBGFrame(PHPDBGBase.FRAME_RAWDATA);
246         
247                 DBGFrame1.addInt(0);                                            // istr = raw data ID
248                 DBGFrame1.addInt(1);                                            // scope_id = -1 means current location, 0 never used, +1 first depth
249
250                 /*              
251                 String evalBlock= new String("$GLOBALS");
252                 DBGFrame2.addInt(1);                                            // FRAME_RAWDATA ID
253                 DBGFrame2.addInt(evalBlock.length() + 1);       // length of rawdata (+ null char)
254                 DBGFrame2.addString(evalBlock);                         // eval block
255                 DBGFrame2.addChar('\0');                                        // null char
256                 */
257                 
258                 // Add command data
259                 DBGPacket.addFrame(DBGFrame1);
260                 
261                 if(proxy.getSocket().isClosed()) return null;
262                 DBGPacket.sendPacket(os);
263
264                 waitResponse(1000);
265                 flushAllPackets();
266                 
267                 // Process serialized variables
268                 DBGVariableList= procVars(stack);
269
270                 return DBGVariableList;
271         }
272
273         public void evalBlock(String evalString) throws IOException, DebugException  {
274                 PHPDBGPacket DBGPacket= new PHPDBGPacket(PHPDBGBase.DBGA_REQUEST);
275                 PHPDBGFrame DBGFrame1= new PHPDBGFrame(PHPDBGBase.FRAME_EVAL);
276                 PHPDBGFrame DBGFrame2= new PHPDBGFrame(PHPDBGBase.FRAME_RAWDATA);
277
278                 rawCounter++;
279                 DBGFrame1.addInt(rawCounter);                           // istr = raw data ID
280                 DBGFrame1.addInt(1);                                            // scope_id = -1 means current location, 0 never used, +1 first depth
281
282                 DBGFrame2.addInt(rawCounter);                           // FRAME_RAWDATA ID
283                 DBGFrame2.addInt(evalString.length() + 1);      // length of rawdata (+ null char)
284                 DBGFrame2.addString(evalString);                        // eval block
285                 DBGFrame2.addChar('\0');                                        // null char
286
287                 // Add raw data first
288                 DBGPacket.addFrame(DBGFrame2);          
289                 // Add command data
290                 DBGPacket.addFrame(DBGFrame1);
291                 
292                 if(proxy.getSocket().isClosed()) return;
293                 DBGPacket.sendPacket(os);
294
295                 waitResponse(1000);
296                 flushAllPackets();
297         }
298
299         public void flushAllPackets() throws IOException {
300                 while(readResponse() != 0);
301         }
302
303         public String getModByNo(int modNo) {
304                 int i;
305                 PHPDBGMod dbg_mod;
306
307                 // look for mod
308                 for(i=0; i < DBGMods.size(); i++) {
309                         dbg_mod= (PHPDBGMod) DBGMods.get(i);
310                         if(dbg_mod.getNo() == modNo) {
311                                 return dbg_mod.getName(); 
312                         }
313                 }
314                 return "";
315         }
316
317         private int getModByName(String modName) {
318                 int i;
319                 PHPDBGMod dbg_mod;
320
321                 // look for mod
322                 for(i=0; i < DBGMods.size(); i++) {
323                         dbg_mod= (PHPDBGMod) DBGMods.get(i);
324                         if(dbg_mod.getName().equalsIgnoreCase(modName)) {
325                                 return dbg_mod.getNo(); 
326                         }
327                 }
328                 return -1;
329         }
330
331         private String getRawFrameData(char[] framesInfo, int frameNo) {
332                 int nextFrame= 0;
333                 int[] dbg_frame= new int[2];
334                 
335                 while(nextFrame < framesInfo.length) {
336                         dbg_frame[0] = PHPDBGBase.Char4ToInt(framesInfo, nextFrame);            // frame name
337                         dbg_frame[1] = PHPDBGBase.Char4ToInt(framesInfo, nextFrame + 4);        // frame size
338
339                         nextFrame += 8;
340                         if(dbg_frame[1] == 0) return "";
341
342                         switch(dbg_frame[0]) {
343                                 case PHPDBGBase.FRAME_RAWDATA:
344                                         if(frameNo == PHPDBGBase.Char4ToInt(framesInfo, nextFrame)) {
345                                                 int toRead= PHPDBGBase.Char4ToInt(framesInfo, nextFrame + 4);
346                                                 return String.copyValueOf(framesInfo, nextFrame + 8, toRead);
347                                         }
348                                         break;
349                         }
350                         // go to next frame
351                         nextFrame += dbg_frame[1];
352                 }
353                 return "";
354         }
355
356         public PHPVariable[] getInstVars(PHPVariable phpVar) throws DebugException {
357                 Vector vecVars= new Vector();
358                 PHPVariable localPHPVar;
359                 int i=0;
360                 
361                 // already unserialized
362                 for(i=0; i < DBGVars.size(); i++) {
363                         localPHPVar= (PHPVariable)DBGVars.get(i);
364                         if(localPHPVar.getParent() == phpVar) {
365                                 vecVars.add(localPHPVar);
366                         }
367                 }
368                 PHPVariable[] arrVars= new PHPVariable[vecVars.size()];
369                 arrVars= (PHPVariable[]) vecVars.toArray(arrVars);
370
371                 return arrVars;
372         }
373         
374         private PHPVariable[] procVars(PHPStackFrame stack) throws DebugException {
375                 Vector vecVars= new Vector();
376                 
377                 // unserialize
378                 finalPos= 0;
379                 refCounter= 0;
380                 doUnserialize(stack, vecVars, null);
381
382                 DBGVars= vecVars;
383                 
384                 return(getInstVars(null));
385         }
386
387         private String readValue(String serialVars) throws DebugException {
388                 int startPos=0, endPos=0, lenStr=0, i=0, elements=0;
389                 String ret= new String("");
390
391                 switch(serialVars.charAt(0)) {
392                         case 'a':       // associative array, a:elements:{[index][value]...}
393                                 typeRead= "hash";
394                                 startPos= 1;
395                                 endPos= serialVars.indexOf(':', startPos + 1);
396                                 if(endPos == -1) return "";
397                                 finalPos += endPos + 2;
398                                 ret= new String(serialVars.substring(startPos + 1, endPos));
399                                 
400                                 hasChildren= true;
401                                 break;
402                         case 'O':       // object, O:name_len:"name":elements:{[attribute][value]...}
403                                 typeRead= "object";
404                                 
405                                 startPos= 1;
406                                 endPos= serialVars.indexOf(':', startPos + 1);
407                                 if(endPos == -1) return "";
408                                 
409                                 // get object class
410                                 lenStr= Integer.parseInt(serialVars.substring(startPos + 1, endPos));
411                                 startPos= endPos + 2;
412                                 endPos= lenStr + startPos;
413                                 className= new String(serialVars.substring(startPos, endPos).toString());
414
415                                 // get num of elements
416                                 startPos= endPos + 1;
417                                 endPos= serialVars.indexOf(':', startPos + 1);
418                                 if(endPos == -1) return "";
419                                 finalPos += endPos + 2;
420                                 ret= new String(serialVars.substring(startPos + 1, endPos));
421
422                                 isObject= true;
423                                 hasChildren= true;                              
424                                 break;
425                         case 's':       // string, s:length:"data";
426                                 typeRead= "string";
427                                 startPos= 1;
428                                 endPos= serialVars.indexOf(':', startPos + 1);
429                                 if(endPos == -1) return "";
430
431                                 lenStr= Integer.parseInt(serialVars.substring(startPos + 1, endPos));
432                                 startPos= endPos + 2;
433                                 endPos= lenStr + startPos;
434                                 ret= new String(serialVars.substring(startPos, endPos).toString());
435                                 finalPos += endPos + 2; 
436                                 break;
437                         case 'i':       // integer, i:123;
438                                 typeRead= "integer";
439                                 startPos= 1;
440                                 endPos= serialVars.indexOf(';', startPos + 1);
441                                 if(endPos == -1) return "";
442
443                                 ret= new String(serialVars.substring(startPos + 1, endPos).toString());
444                                 finalPos += endPos + 1;
445                                 break;
446                         case 'd':       // double (float), d:1.23;
447                                 typeRead= "double";
448                                 startPos= 1;
449                                 endPos= serialVars.indexOf(';', startPos + 1);
450                                 if(endPos == -1) return "";
451         
452                                 ret= new String(serialVars.substring(startPos + 1, endPos).toString());
453                                 finalPos += endPos + 1;
454                                 break;
455                         case 'N':       // NULL, N;
456                                 typeRead= "null";
457                                 ret= "nil";
458                                 finalPos += 2;
459                                 break;
460                         case 'b':       // bool, b:0 or 1
461                                 typeRead= "boolean";
462                                 ret= (serialVars.charAt(2) == '1')?"true":"false";
463                                 finalPos += endPos + 4;
464                                 break;
465                         case 'z':       // resource, z:typename_len:"typename":valres;
466                                 typeRead= "resource";
467                                 
468                                 startPos= 1;
469                                 endPos= serialVars.indexOf(':', startPos + 1);
470                                 if(endPos == -1) return "";
471                 
472                                 // get resource type name
473                                 lenStr= Integer.parseInt(serialVars.substring(startPos + 1, endPos));
474                                 startPos= endPos + 2;
475                                 endPos= lenStr + startPos;
476                                 className= new String(serialVars.substring(startPos, endPos).toString());
477
478                                 // get resource value
479                                 startPos= endPos + 1;
480                                 endPos= serialVars.indexOf(';', startPos + 1);
481                                 if(endPos == -1) return "";
482                                 ret= new String(serialVars.substring(startPos + 1, endPos));
483                                 finalPos += endPos + 1;
484                                 break;
485                         case 'r':
486                         case 'R':
487                                 typeRead= "reference";
488                                 startPos= 1;
489                                 endPos= serialVars.indexOf(';', startPos + 1);
490                                 if(endPos == -1) return "0";
491
492                                 ret= new String(serialVars.substring(startPos + 1, endPos));
493                                 finalPos += endPos + 1;
494                                 isRef= true;
495                                 break;
496                         case ';':
497                                 typeRead= "unknown";
498                                 finalPos+= 1;
499                                 break;
500                         case '?':
501                                 finalPos+= 1;
502                         default:
503                                 finalPos+= 1;
504                                 typeRead= "unknown";
505                                 break;
506                 }
507                 return ret;
508         }
509
510         private void doUnserialize(PHPStackFrame stack, Vector vecVars, PHPVariable parent) throws DebugException {
511                 int i, elements= 0;
512                 PHPVariable newVar= null;
513                 String value= new String("");
514                 String name= new String("");
515                 String tmp= new String("");
516                 String[] tmpSplit;
517
518                 if(finalPos > serGlobals.length() || serGlobals.equals("") || serGlobals.substring(finalPos).equals("")) return;
519
520                 isRef= false;
521                 hasChildren= false;
522                 isObject= false;
523                 name= readValue(serGlobals.substring(finalPos));
524                 
525                 if(hasChildren) {
526                         // main array
527                         if(refCounter == 0) {
528                                 value= name;
529                                 name= "";
530                         }
531                 } else {
532                         hasChildren= false;
533                         isRef= false;
534                         value= readValue(serGlobals.substring(finalPos));
535                         // replaceAll doesn't work, why???
536                         tmpSplit= value.split("\\\\");
537                         value= "";
538                         for(i= 0; i < tmpSplit.length; i++) {
539                                 value= value + tmpSplit[i];
540                                 if(!tmpSplit[i].equals("")) {
541                                         if(i < (tmpSplit.length - 1)) {
542                                                 value= value + "\\";
543                                         }
544                                 }
545                         }
546                 }
547                 
548                 if(!name.equals("")) {
549                         if(isRef) {
550                                 PHPVariable varPHP;
551                                 for(i=0; i < vecVars.size(); i++) {
552                                         varPHP= (PHPVariable) vecVars.get(i);
553                                         if(varPHP.getObjectId().equals(value)) {
554                                                 newVar= new PHPVariable(stack, name, "local", true, (PHPValue)varPHP.getValue());
555                                                 break;                                          
556                                         }
557                                 }
558                                 if(newVar == null) {
559                                         newVar= new PHPVariable(stack, name, "local", false, null);
560                                 }
561                         } else {
562                                 refCounter++;
563                                 newVar= new PHPVariable(stack, name, "local", value, typeRead, hasChildren, Integer.toString(refCounter), className);
564                         }
565                         newVar.setParent(parent);
566                         vecVars.add(newVar);
567                 }
568                 if(hasChildren) {
569                         elements= Integer.parseInt(value);
570                         for(i=0; i < elements; i++)
571                                 doUnserialize(stack, vecVars, newVar);
572
573                         // skip "}"
574                         finalPos += 1;
575                 }
576         }
577
578         public int readResponse() throws IOException {
579                 int bytesToRead=0, nextFrame=0, i=0, cmdReceived=0, stackIndex=0;
580                 char[] dbg_header_struct_read= new char[16];
581                 int[] dbg_header_struct= new int[4];
582                 int[] dbg_bpl_tmp= new int[10];
583                 int[] dbg_frame= new int[2];
584                 int[] dbg_eval_tmp= new int[3];
585                 int[] dbg_src_tree_tmp= new int[4];
586                 Vector rawList= new Vector();
587                 Vector stackList= new Vector();
588                 PHPStackFrame[] newStackList;
589                 
590                 rawList.clear();
591                 stackList.clear();
592                 // Read from input
593                 while(readInput(dbg_header_struct_read, 16) != 0) {
594                         dbg_header_struct[0] = PHPDBGBase.Char4ToInt(dbg_header_struct_read, 0);
595                         dbg_header_struct[1] = PHPDBGBase.Char4ToInt(dbg_header_struct_read, 4);
596                         dbg_header_struct[2] = PHPDBGBase.Char4ToInt(dbg_header_struct_read, 8);
597                         dbg_header_struct[3] = PHPDBGBase.Char4ToInt(dbg_header_struct_read, 12);
598                         
599                         // Check DBG sync bytes
600                         if(dbg_header_struct[0] != 0x5953) return 0;
601                         
602                         cmdReceived= dbg_header_struct[1];
603                         setLastCmd(cmdReceived);
604                         bytesToRead= dbg_header_struct[3];
605
606                         //System.out.println("Response Received: " + cmdReceived);
607                         char[] entirePack= new char[bytesToRead];
608
609                         if(bytesToRead > 0) {
610                                 if(readInput(entirePack, bytesToRead) < bytesToRead) return 0;
611                         }
612                         
613                         // First process frames
614                         nextFrame= 0;
615                         while(nextFrame < bytesToRead) {
616                                 dbg_frame[0] = PHPDBGBase.Char4ToInt(entirePack, nextFrame);            // frame name
617                                 dbg_frame[1] = PHPDBGBase.Char4ToInt(entirePack, nextFrame + 4);        // frame size
618                                 nextFrame += 8;
619                                 if(dbg_frame[1] == 0) return 0;
620                                 switch(dbg_frame[0]) {
621                                         case PHPDBGBase.FRAME_STACK:
622                                                 int[] dbg_stack_new= new int[4];
623                                                 dbg_stack_new[0] = PHPDBGBase.Char4ToInt(entirePack, nextFrame + 0);    // line no
624                                                 dbg_stack_new[1] = PHPDBGBase.Char4ToInt(entirePack, nextFrame + 4);    // mod no
625                                                 dbg_stack_new[2] = PHPDBGBase.Char4ToInt(entirePack, nextFrame + 8);    // scope id
626                                                 dbg_stack_new[3] = PHPDBGBase.Char4ToInt(entirePack, nextFrame + 12);   // id of description string
627
628                                                 stackIndex++;
629                                                 if(dbg_stack_new[1] != 0) {                                             
630                                                         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]);
631                                                         stackList.add(newStack);
632                                                 }
633                                                 break;
634                                         case PHPDBGBase.FRAME_SOURCE:
635                                                 break;
636                                         case PHPDBGBase.FRAME_SRC_TREE:
637                                                 dbg_src_tree_tmp[0] = PHPDBGBase.Char4ToInt(entirePack, nextFrame + 0);         // parent_mod_no
638                                                 dbg_src_tree_tmp[1] = PHPDBGBase.Char4ToInt(entirePack, nextFrame + 4);         // parent_line_no               /* NOT USED */
639                                                 dbg_src_tree_tmp[2] = PHPDBGBase.Char4ToInt(entirePack, nextFrame + 8);         // mod_no
640                                                 dbg_src_tree_tmp[3] = PHPDBGBase.Char4ToInt(entirePack, nextFrame + 12);        // imod_name
641
642                                                 if(getModByNo(dbg_src_tree_tmp[2]).equals("")) {
643                                                         String fileName= new String(getRawFrameData(entirePack, dbg_src_tree_tmp[3]));
644                                                         // Remove '\0' char
645                                                         if(fileName.length() > 0) fileName= fileName.substring(0, fileName.length() - 1);
646
647                                                         if(dbg_src_tree_tmp[2] != 0) {
648                                                                 PHPDBGMod modNew= new PHPDBGMod(dbg_src_tree_tmp[2], fileName);
649                                                                 DBGMods.add(modNew);
650                                                         }
651                                                 }
652                                                 break;
653                                         case PHPDBGBase.FRAME_RAWDATA:
654                                                 break;
655                                         case PHPDBGBase.FRAME_ERROR:
656                                                 break;
657                                         case PHPDBGBase.FRAME_EVAL:
658                                                 String evalString= new String("");
659                                                 dbg_eval_tmp[0] = PHPDBGBase.Char4ToInt(entirePack, nextFrame + 0); // istr
660                                                 dbg_eval_tmp[1] = PHPDBGBase.Char4ToInt(entirePack, nextFrame + 4); // iresult
661                                                 dbg_eval_tmp[2] = PHPDBGBase.Char4ToInt(entirePack, nextFrame + 8); // ierror
662
663                                                 evalRet= getRawFrameData(entirePack, dbg_eval_tmp[1]);
664                                                 evalString= getRawFrameData(entirePack, dbg_eval_tmp[0]);
665                                                 serGlobals= evalRet;
666                                                 break;
667                                         case PHPDBGBase.FRAME_BPS:
668                                                 break;
669                                         case PHPDBGBase.FRAME_BPL:
670                                                 int[] dbg_bpl_new= new int[10];
671                                                 dbg_bpl_new[0] = PHPDBGBase.Char4ToInt(entirePack, nextFrame + 0);
672                                                 dbg_bpl_new[1] = PHPDBGBase.Char4ToInt(entirePack, nextFrame + 4);
673                                                 dbg_bpl_new[2] = PHPDBGBase.Char4ToInt(entirePack, nextFrame + 8);
674                                                 dbg_bpl_new[3] = PHPDBGBase.Char4ToInt(entirePack, nextFrame + 12);
675                                                 dbg_bpl_new[4] = PHPDBGBase.Char4ToInt(entirePack, nextFrame + 16);
676                                                 dbg_bpl_new[5] = PHPDBGBase.Char4ToInt(entirePack, nextFrame + 20);
677                                                 dbg_bpl_new[6] = PHPDBGBase.Char4ToInt(entirePack, nextFrame + 24);
678                                                 dbg_bpl_new[7] = PHPDBGBase.Char4ToInt(entirePack, nextFrame + 28);
679                                                 dbg_bpl_new[8] = PHPDBGBase.Char4ToInt(entirePack, nextFrame + 32);
680                                                 dbg_bpl_new[9] = PHPDBGBase.Char4ToInt(entirePack, nextFrame + 36);
681         
682                                                 // look if breakpoint already exists in vector
683                                                 for(i=0; i < DBGBPList.size(); i++) {
684                                                         dbg_bpl_tmp= (int[]) DBGBPList.get(i);
685                                                         if(dbg_bpl_tmp[8] == dbg_bpl_new[8]) {
686                                                                 DBGBPList.remove(i);
687                                                                 break;
688                                                         }
689                                                 }
690
691                                                 // add breakpoint to vector
692                                                 DBGBPList.add(dbg_bpl_new);
693                                                 copyToLastBP(dbg_bpl_new);
694                                                 
695                                                 // mod no returned?
696                                                 if(getModByNo(dbg_bpl_new[0]).equals("")) {
697                                                         String fileName= new String(getRawFrameData(entirePack, dbg_bpl_new[2]));
698                                                         // Remove '\0' char
699                                                         if(fileName.length() > 0) fileName= fileName.substring(0, fileName.length() - 1);
700                                                         if(dbg_bpl_new[0] != 0) {
701                                                                 PHPDBGMod modNew= new PHPDBGMod(dbg_bpl_new[0], fileName);
702                                                                 DBGMods.add(modNew);
703                                                         }
704                                                 }                                                       
705                                                 break;
706                                         case PHPDBGBase.FRAME_VER:
707                                                 break;
708                                         case PHPDBGBase.FRAME_SID:
709                                           sid = PHPDBGBase.Char4ToInt(entirePack, nextFrame + 0);
710                                                 break;
711                                         case PHPDBGBase.FRAME_SRCLINESINFO:
712                                                 break;
713                                         case PHPDBGBase.FRAME_SRCCTXINFO:
714                                                 break;
715                                         case PHPDBGBase.FRAME_LOG:
716                                                 break;
717                                         case PHPDBGBase.FRAME_PROF:
718                                                 break;
719                                         case PHPDBGBase.FRAME_PROF_C:
720                                                 break;
721                                         case PHPDBGBase.FRAME_SET_OPT:
722                                                 break;
723                                 }
724                                 // go to next frame
725                                 nextFrame += dbg_frame[1];
726                         }
727                         
728                         // Now process command
729                         switch(cmdReceived) {
730                                 case PHPDBGBase.DBGC_REPLY:
731                                         break;
732                                 case PHPDBGBase.DBGC_STARTUP:
733                                         break;
734                                 case PHPDBGBase.DBGC_END:
735                                         sessionEnded= true;
736                                         break;
737                                 case PHPDBGBase.DBGC_BREAKPOINT:
738                                         newStackList= new PHPStackFrame[stackList.size()];
739                                         newStackList= (PHPStackFrame[]) stackList.toArray(newStackList);
740                                         DBGStackList= newStackList;
741                                         BPUnderHit= getBPUnderHit();
742                                         break;
743                                 case PHPDBGBase.DBGC_STEPINTO_DONE:
744                                 case PHPDBGBase.DBGC_STEPOVER_DONE:
745                                 case PHPDBGBase.DBGC_STEPOUT_DONE:
746                                 case PHPDBGBase.DBGC_EMBEDDED_BREAK:
747                                         BPUnderHit= 1;
748                                         newStackList= new PHPStackFrame[stackList.size()];
749                                         newStackList= (PHPStackFrame[]) stackList.toArray(newStackList);
750                                         DBGStackList= newStackList;
751                                         break;
752                                 case PHPDBGBase.DBGC_ERROR:
753                                         newStackList= new PHPStackFrame[stackList.size()];
754                                         newStackList= (PHPStackFrame[]) stackList.toArray(newStackList);
755                                         DBGStackList= newStackList;
756                                         break;
757                                 case PHPDBGBase.DBGC_LOG:
758                                         break;
759                                 case PHPDBGBase.DBGC_SID:
760                                         break;
761                                 case PHPDBGBase.DBGC_PAUSE:
762                                         break;
763                         }
764                 }
765
766                 return cmdReceived;
767         }
768
769         public PHPStackFrame[] getStackList() {
770                 return DBGStackList;
771         }
772
773         private int readInput(char[] buffer, int bytes) throws IOException {
774                 int bytesRead= 0;
775
776                 for(int i=0; i < bytes; i++) {
777                         if(in.ready()) {
778                                 buffer[i]= (char) (in.read() & 0x00FF);
779                                 bytesRead++;
780                         }
781                         else
782                                 break;                          
783                 }
784                 return bytesRead;
785         }
786         
787         public void setShouldStop() {
788                 this.shouldStop= true;
789         }
790
791         public boolean waitResponse(long milliseconds) throws IOException {
792                 long timeout= System.currentTimeMillis() + milliseconds;
793                 while(System.currentTimeMillis() < timeout) {
794                         if(in.ready() || shouldStop) {
795                                 break;
796                         }
797                 }
798                 return in.ready();
799         }
800 }