void read_trace_file(ifstream & in, CCNode * root) { HeapObject * heapObject; HeapObject * targetObject; // CCNode * current_node = root; theStack[0] = root; threadStarts[0] = root; CCNode * node; int depth = 0; int time = 0; bool in_death_records = false; int last_epoch_time = 0; int last_thread_id = 0; while (in.good()) { char kind; string line; int object_id; int dtime; int size; string type; int method_id; string class_name; string method_name; string signature; int old_target; int new_target; int thread_id; Method * method; in >> kind; // in >> hex >> time; /* if (in_death_records && (kind != 'D')) { in_death_records = false; last_epoch_time = time; } */ switch (kind) { case 'A': { in >> hex >> object_id; in >> hex >> size; in >> type; in >> hex >> thread_id; CCNode * curContext = 0; if (thread_id == object_id) { // -- Spawning a new thread -- make it a child of the root curContext = root; // theStack[last_thread_id]; CCNode * newContext = curContext->demand_child(method_id, thread_id, time); newContext->incCalls(); theStack[thread_id] = newContext; if (debug > 0) cout << "Spawn thread 0x" << hex << thread_id << dec << endl; } curContext = theStack[thread_id]; curContext->incAllocBytes(size); curContext->incAllocObjects(); heapObject = HeapObject::DemandHeapObject(object_id); heapObject->setAlloc(time, size, type); heapObject->setAllocCC(curContext); if (debug > 0) { cout << "Allocate 0x" << hex << object_id << " size 0x" << size << dec << " at time " << time << endl; if (debug > 1) curContext->printStack(); } last_thread_id = thread_id; } objects.push_back(object_id); break; case 'D': { in >> hex >> object_id; heapObject = HeapObject::DemandHeapObject(object_id); heapObject->setDead(time); (HeapObject::Find(heapObject))->incNumDead(); CCNode * curContext = theStack[last_thread_id]; curContext->incDeadBytes(heapObject->getSize()); curContext->incDeadObjects(); heapObject->setDeathCC(curContext); } break; case 'U': in >> hex >> old_target; in >> hex >> object_id; in >> hex >> new_target; if (new_target != 0) { heapObject = HeapObject::DemandHeapObject(object_id); targetObject = HeapObject::DemandHeapObject(new_target); HeapObject::Union(heapObject, targetObject); if (debug > 0) { cout << "Pointer from 0x" << hex << object_id << " to 0x" << new_target << dec << " at time " << time << endl; if (debug > 1) { CCNode * curContext = theStack[last_thread_id]; curContext->printStack(); } } } break; case 'M': { in >> hex >> method_id; in >> hex >> object_id; in >> hex >> thread_id; CCNode * curContext = theStack[thread_id]; bool new_thread = false; if (curContext == 0) { // -- Spawning a new thread -- look up the place where the thread was started // Relies on the fact that the thread_id is the same as the object_id of // the Thread object instance. new_thread = true; curContext = threadStarts[thread_id]; if (curContext) { // if (debug > 0) cout << "Spawn thread 0x" << hex << thread_id << dec << " -- started at " << curContext->getMethodFullName() << endl; cout << " in context" << endl; curContext->printStack(); } else { cout << "Problem: no threadStart for thread id 0x" << hex << thread_id << dec << endl; curContext = root; } } time++; depth++; curContext = curContext->demand_child(method_id, thread_id, time); curContext->incCalls(); theStack[thread_id] = curContext; if (debug > 0 or new_thread) { cout << "Enter " << curContext->getMethodFullName() << " 0x" << hex << method_id << " thread 0x" << thread_id << " at time " << time << endl; if (debug > 1) curContext->printStack(); } if (method_id == thread_start_method_id) { // -- Found a new thread start threadStarts[object_id] = curContext; thread_number++; threadIdNumbering[object_id] = thread_number; if (true) { cout << "Found Thread.start at " << endl; curContext->printStack(); } } last_thread_id = thread_id; } break; case 'E': { in >> hex >> method_id; in >> hex >> object_id; in >> hex >> thread_id; CCNode * curContext = theStack[thread_id]; if (debug > 0) { cout << hex << "E " << method_id << " " << object_id << " " << thread_id << endl; //cout << "Exit " << curContext->getMethodFullName() << " 0x" << hex << method_id << " thread 0x" << thread_id << " at time " << time << endl; cout << "Exit: Looking for " << "0x" << hex << method_id << " reciever: 0x" << object_id << " thread: 0x" << thread_id << endl; if (debug > 1) curContext->printStack(); } time++; CCNode * returning = curContext; int cur_id = returning->getMethodId(); int orig_depth = depth; while (returning and returning->getMethodId() != method_id) { returning = returning->getParent(); depth--; } if (returning == 0) { cout << "THIS IS BAD: looking for " << hex << "0x" << method_id << " but found 0x" << cur_id << dec << endl; returning->printStack(); // current_node unchanged depth = orig_depth; } else { // cout << "Return " << current_node->getMethodFullName() << "(" << hex << current_node->getMethodId() << dec << ")" << endl; returning->setLastCall(time); theStack[thread_id] = returning->getParent(); depth--; } last_thread_id = thread_id; } break; default: cout << "UNKNOWN" << endl; break; } getline(in, line); record_count++; if (record_count % 1000000 == 0) { cerr << "At " << record_count << endl; } } }