+/* Write the process state of the trace */
+
+static void write_process_state(gpointer key, gpointer value,
+ gpointer user_data)
+{
+ LttvProcessState *process;
+
+ LttvExecutionState *es;
+
+ FILE *fp = (FILE *)user_data;
+
+ guint i;
+
+ process = (LttvProcessState *)value;
+ fprintf(fp,
+" <PROCESS PID=%u PPID=%u CTIME_S=%lu CTIME_NS=%lu NAME=\"%s\" CPU=\"%s\">\n",
+ process->pid, process->ppid, process->creation_time.tv_sec,
+ process->creation_time.tv_nsec, g_quark_to_string(process->name),
+ g_quark_to_string(process->last_cpu));
+
+ for(i = 0 ; i < process->execution_stack->len; i++) {
+ es = &g_array_index(process->execution_stack, LttvExecutionState, i);
+ fprintf(fp, " <ES MODE=\"%s\" SUBMODE=\"%s\" ENTRY_S=%lu ENTRY_NS=%lu",
+ g_quark_to_string(es->t), g_quark_to_string(es->n),
+ es->entry.tv_sec, es->entry.tv_nsec);
+ fprintf(fp, " CHANGE_S=%lu CHANGE_NS=%lu STATUS=\"%s\"/>\n",
+ es->change.tv_sec, es->change.tv_nsec, g_quark_to_string(es->s));
+ }
+ fprintf(fp, " </PROCESS>\n");
+}
+
+
+void lttv_state_write(LttvTraceState *self, LttTime t, FILE *fp)
+{
+ guint i, nb_tracefile, nb_block, nb_event;
+
+ LttvTracefileState *tfcs;
+
+ LttTracefile *tf;
+
+ LttEventPosition *ep;
+
+ ep = ltt_event_position_new();
+
+ fprintf(fp,"<PROCESS_STATE TIME_S=%lu TIME_NS=%lu>\n", t.tv_sec, t.tv_nsec);
+
+ g_hash_table_foreach(self->processes, write_process_state, fp);
+
+ nb_tracefile = ltt_trace_control_tracefile_number(self->parent.t) +
+ ltt_trace_per_cpu_tracefile_number(self->parent.t);
+
+ for(i = 0 ; i < nb_tracefile ; i++) {
+ tfcs = (LttvTracefileState *)self->parent.tracefiles[i];
+ fprintf(fp, " <TRACEFILE PID=%u", tfcs->process->pid);
+ if(tfcs->parent.e == NULL) fprintf(fp,"/>\n");
+ else {
+ ltt_event_position(tfcs->parent.e, ep);
+ ltt_event_position_get(ep, &nb_block, &nb_event, &tf);
+ fprintf(fp, " BLOCK=%u EVENT=%u/>\n", nb_block, nb_event);
+ }
+ }
+ g_free(ep);
+ fprintf(fp,"</PROCESS_STATE>");
+}
+
+
+/* Copy each process from an existing hash table to a new one */
+