updates Various formatting fixes.

Sat Apr 22 15:08:01 2006  Soeren Sandmann  <sandmann@redhat.com>

	* TODO: updates
	* profile.c, sfile.c, sformat.c: Various formatting fixes.
This commit is contained in:
Soeren Sandmann
2006-04-22 19:08:23 +00:00
committed by Søren Sandmann Pedersen
parent 6c36cd060c
commit e97dcc792a
5 changed files with 416 additions and 392 deletions

View File

@ -1,3 +1,8 @@
Sat Apr 22 15:08:01 2006 Soeren Sandmann <sandmann@redhat.com>
* TODO: updates
* profile.c, sfile.c, sformat.c: Various formatting fixes.
Wed Apr 5 11:26:30 2006 Søren Sandmann <sandmann@redhat.com>
* TODO: updates

15
TODO
View File

@ -30,8 +30,6 @@ Before 1.2:
* commandline version should check that the output file is writable
before starting the profiling.
* screenshot window must be cleared when you press start.
* Maybe report idle time?
* Fix (deleted) problem. But more generally, whenever we can't display a
@ -138,7 +136,8 @@ Before 1.2:
int id; -> for begins that are pointed to
}
perhaps even with iterators. Should be compact and suitable for both
input and output..
input and output. As a first cut, perhaps just split out the
Instruction code.
- make the api saner; add format/content structs
@ -312,11 +311,11 @@ Later:
Profiling itself it appeared that most of the time was spent
in the GMarkup parser
- a newer version of sysprof with significantly more compact
Instructions took about 5 seconds, but the profile looked
about the same.
Instructions structure took about 5 seconds, but the profile
looked about the same.
The difference between the two versions has to be in page faults/
memory speed, but the profiles looked identically.
Try and reproduce this result in a more controlled experiment.
memory speed, but the profiles looked similar.
Try and reproduce this in a more controlled experiment.
- See if it is possible to group the X server activity under the process that
generated it.
@ -495,6 +494,8 @@ Later:
DONE:
- screenshot window must be cleared when you press start.
- Formats should become first-class, stand-alone objects that offers
help with parsing and nothing else.

View File

@ -31,7 +31,7 @@ typedef struct Node Node;
struct Profile
{
StackStash * stash;
StackStash *stash;
};
static SFormat *
@ -470,7 +470,7 @@ profile_free (Profile *profile)
}
void
profile_descendant_free (ProfileDescendant *descendant)
profile_descendant_free (ProfileDescendant *descendant)
{
if (!descendant)
return;

207
sfile.c
View File

@ -29,60 +29,6 @@
#include "sfile.h"
#include "sformat.h"
static void
set_error (GError **err, gint code, const char *format, va_list args)
{
char *msg;
if (!err)
return;
msg = g_strdup_vprintf (format, args);
if (*err == NULL)
{
*err = g_error_new_literal (G_MARKUP_ERROR, code, msg);
}
else
{
/* Warning text from GLib */
g_warning ("GError set over the top of a previous GError or uninitialized memory.\n"
"This indicates a bug in someone's code. You must ensure an error is NULL before it's set.\n"
"The overwriting error message was: %s",
msg);
}
g_free (msg);
}
static void
set_unknown_element_error (GError **err, const char *format, ...)
{
va_list args;
va_start (args, format);
set_error (err, G_MARKUP_ERROR_UNKNOWN_ELEMENT, format, args);
va_end (args);
}
static void
set_unknown_attribute_error (GError **err, const char *format, ...)
{
va_list args;
va_start (args, format);
set_error (err, G_MARKUP_ERROR_UNKNOWN_ATTRIBUTE, format, args);
va_end (args);
}
static void
set_invalid_content_error (GError **err, const char *format, ...)
{
va_list args;
va_start (args, format);
set_error (err, G_MARKUP_ERROR_INVALID_CONTENT, format, args);
va_end (args);
}
/* reading */
typedef struct BuildContext BuildContext;
typedef struct Instruction Instruction;
typedef enum
@ -137,6 +83,63 @@ struct BuildContext
GArray *instructions;
};
static void
set_error (GError **err,
gint code,
const char *format,
va_list args)
{
char *msg;
if (!err)
return;
msg = g_strdup_vprintf (format, args);
if (*err == NULL)
{
*err = g_error_new_literal (G_MARKUP_ERROR, code, msg);
}
else
{
/* Warning text from GLib */
g_warning ("GError set over the top of a previous GError or uninitialized memory.\n"
"This indicates a bug in someone's code. You must ensure an error is NULL before it's set.\n"
"The overwriting error message was: %s",
msg);
}
g_free (msg);
}
static void
set_unknown_element_error (GError **err, const char *format, ...)
{
va_list args;
va_start (args, format);
set_error (err, G_MARKUP_ERROR_UNKNOWN_ELEMENT, format, args);
va_end (args);
}
static void
set_unknown_attribute_error (GError **err, const char *format, ...)
{
va_list args;
va_start (args, format);
set_error (err, G_MARKUP_ERROR_UNKNOWN_ATTRIBUTE, format, args);
va_end (args);
}
static void
set_invalid_content_error (GError **err, const char *format, ...)
{
va_list args;
va_start (args, format);
set_error (err, G_MARKUP_ERROR_INVALID_CONTENT, format, args);
va_end (args);
}
/* reading */
static gboolean
is_all_blank (const char *text)
{
@ -212,8 +215,8 @@ sfile_get_pointer (SFileInput *file,
instruction = file->current_instruction++;
g_return_if_fail (stype_is_pointer (instruction->type));
instruction->u.pointer.location = location;
instruction->u.pointer.location = location;
*location = (gpointer) 0xFedeAbe;
@ -227,9 +230,9 @@ sfile_get_pointer (SFileInput *file,
}
void
sfile_get_integer (SFileInput *file,
const char *name,
gint32 *integer)
sfile_get_integer (SFileInput *file,
const char *name,
gint32 *integer)
{
Instruction *instruction;
@ -241,9 +244,9 @@ sfile_get_integer (SFileInput *file,
}
void
sfile_get_string (SFileInput *file,
const char *name,
char **string)
sfile_get_string (SFileInput *file,
const char *name,
char **string)
{
Instruction *instruction;
@ -259,15 +262,11 @@ hook_up_pointers (SFileInput *file)
{
int i;
#if 0
g_print ("emfle\n");
#endif
for (i = 0; i < file->n_instructions; ++i)
{
Instruction *instruction = &(file->instructions[i]);
if (instruction->kind == VALUE &&
stype_is_pointer (instruction->type))
if (stype_is_pointer (instruction->type))
{
gpointer target_object;
Instruction *target_instruction;
@ -279,10 +278,6 @@ hook_up_pointers (SFileInput *file)
else
target_object = NULL;
#if 0
g_print ("target object: %p\n", target_object);
#endif
*(instruction->u.pointer.location) = target_object;
}
}
@ -489,7 +484,7 @@ free_instructions (Instruction *instructions, int n_instructions)
{
Instruction *instruction = &(instructions[i]);
if (instruction->kind == VALUE && stype_is_string (instruction->type))
if (stype_is_string (instruction->type))
g_free (instruction->u.string.value);
}
@ -536,7 +531,9 @@ process_instruction_pairs (Instruction *first)
}
static gboolean
post_process_read_instructions (Instruction *instructions, int n_instructions, GError **err)
post_process_read_instructions (Instruction *instructions,
int n_instructions,
GError **err)
{
gboolean retval = TRUE;
GHashTable *instructions_by_id;
@ -565,8 +562,7 @@ post_process_read_instructions (Instruction *instructions, int n_instructions, G
{
Instruction *instruction = &(instructions[i]);
if (instruction->kind == VALUE &&
stype_is_pointer (instruction->type))
if (stype_is_pointer (instruction->type))
{
int target_id = instruction->u.pointer.target_id;
@ -610,7 +606,10 @@ post_process_read_instructions (Instruction *instructions, int n_instructions, G
}
static Instruction *
build_instructions (const char *contents, SFormat *format, int *n_instructions, GError **err)
build_instructions (const char *contents,
SFormat *format,
int *n_instructions,
GError **err)
{
BuildContext build;
GMarkupParseContext *parse_context;
@ -791,9 +790,9 @@ sfile_check_value (SFileOutput *file,
}
void
sfile_add_string (SFileOutput *file,
const char *name,
const char *string)
sfile_add_string (SFileOutput *file,
const char *name,
const char *string)
{
Instruction instruction;
@ -812,9 +811,9 @@ sfile_add_string (SFileOutput *file,
}
void
sfile_add_integer (SFileOutput *file,
const char *name,
int integer)
sfile_add_integer (SFileOutput *file,
const char *name,
int integer)
{
Instruction instruction;
@ -831,9 +830,9 @@ sfile_add_integer (SFileOutput *file,
}
void
sfile_add_pointer (SFileOutput *file,
const char *name,
gpointer pointer)
sfile_add_pointer (SFileOutput *file,
const char *name,
gpointer pointer)
{
Instruction instruction;
@ -898,7 +897,7 @@ post_process_write_instructions (SFileOutput *sfile)
if (!target)
{
g_warning ("pointer has unknown target\n");
return;
goto out;
}
g_assert (target->kind == END);
@ -915,11 +914,14 @@ post_process_write_instructions (SFileOutput *sfile)
}
}
}
out:
g_hash_table_destroy (instructions_by_object);
}
static void
add_indent (GString *output, int indent)
add_indent (GString *output,
int indent)
{
int i;
@ -928,13 +930,15 @@ add_indent (GString *output, int indent)
}
static void
add_integer (GString *output, int value)
add_integer (GString *output,
int value)
{
g_string_append_printf (output, "%d", value);
}
static void
add_string (GString *output, const char *str)
add_string (GString *output,
const char *str)
{
char *escaped = g_markup_escape_text (str, -1);
g_string_append_c (output, '\"');
@ -944,7 +948,10 @@ add_string (GString *output, const char *str)
}
static void
add_begin_tag (GString *output, int indent, const char *name, int id)
add_begin_tag (GString *output,
int indent,
const char *name,
int id)
{
add_indent (output, indent);
@ -955,7 +962,9 @@ add_begin_tag (GString *output, int indent, const char *name, int id)
}
static void
add_end_tag (GString *output, int indent, const char *name)
add_end_tag (GString *output,
int indent,
const char *name)
{
add_indent (output, indent);
g_string_append_printf (output, "</%s>", name);
@ -968,10 +977,10 @@ add_nl (GString *output)
}
static gboolean
file_replace (const gchar *filename,
const gchar *contents,
gssize length,
GError **error);
file_replace (const gchar *filename,
const gchar *contents,
gssize length,
GError **error);
#if 0
static void
@ -1101,8 +1110,10 @@ sfile_output_save (SFileOutput *sfile,
{
add_string (output, instruction->u.string.value);
}
add_end_tag (output, 0, get_name (instruction));
add_nl (output);
add_nl (output);
break;
}
}
@ -1127,7 +1138,7 @@ sfile_output_save (SFileOutput *sfile,
void
sfile_input_free (SFileInput *file)
sfile_input_free (SFileInput *file)
{
free_instructions (file->instructions, file->n_instructions);

577
sformat.c
View File

@ -62,6 +62,296 @@ struct SType
static void type_free (SType *type);
/*
* Transition
*/
typedef enum
{
BEGIN,
VALUE,
END
} TransitionKind;
struct Transition
{
SType * type;
TransitionKind kind;
State * to;
};
static Transition *transition_new (SFormat *format,
TransitionKind kind,
SType *type,
State *from,
State *to);
static void transition_free (Transition *transition);
static void transition_set_to_state (Transition *transition,
State *to_state);
/*
* State
*/
struct State
{
GQueue *transitions;
};
static State *state_new (SFormat *format);
static void state_add_transition (State *state,
Transition *transition);
static void state_free (State *state);
/*
* Format
*/
SFormat *
sformat_new (void)
{
/* FIXME: should probably be refcounted, and an SContext
* should have a ref on the format
*/
SFormat *format = g_new0 (SFormat, 1);
format->begin = NULL;
format->end = NULL;
format->types = g_queue_new ();
format->states = g_queue_new ();
format->transitions = g_queue_new ();
return format;
}
void
sformat_free (SFormat *format)
{
GList *list;
for (list = format->types->head; list; list = list->next)
{
SType *type = list->data;
type_free (type);
}
g_queue_free (format->types);
for (list = format->states->head; list; list = list->next)
{
State *state = list->data;
state_free (state);
}
g_queue_free (format->states);
for (list = format->transitions->head; list; list = list->next)
{
Transition *transition = list->data;
transition_free (transition);
}
g_queue_free (format->transitions);
g_free (format);
}
void
sformat_set_type (SFormat *format,
SType *type)
{
format->begin = state_new (format);
format->end = state_new (format);
state_add_transition (format->begin, type->enter);
transition_set_to_state (type->exit, format->end);
}
/*
* Type
*/
static SType *
type_new (SFormat *format,
TypeKind kind,
const char *name)
{
SType *type = g_new0 (SType, 1);
type->kind = kind;
type->name = name? g_strdup (name) : NULL;
type->enter = NULL;
type->exit = NULL;
type->target = NULL;
g_queue_push_tail (format->types, type);
return type;
}
static SType *
type_new_from_forward (SFormat *format,
TypeKind kind,
const char *name,
SForward *forward)
{
SType *type;
if (forward)
{
type = (SType *)forward;
type->kind = kind;
type->name = g_strdup (name);
}
else
{
type = type_new (format, kind, name);
}
return type;
}
static SType *
type_new_value (SFormat *format, TypeKind kind, const char *name)
{
SType *type = type_new (format, kind, name);
State *before, *after;
Transition *value;
before = state_new (format);
after = state_new (format);
type->enter = transition_new (format, BEGIN, type, NULL, before);
type->exit = transition_new (format, END, type, after, NULL);
value = transition_new (format, VALUE, type, before, after);
return type;
}
static void
type_free (SType *type)
{
g_free (type->name);
g_free (type);
}
SForward *
sformat_declare_forward (SFormat *format)
{
SType *type = type_new (format, TYPE_FORWARD, NULL);
return (SForward *)type;
}
static GQueue *
expand_varargs (SType *content1,
va_list args)
{
GQueue *types = g_queue_new ();
SType *type;
g_queue_push_tail (types, content1);
type = va_arg (args, SType *);
while (type)
{
g_queue_push_tail (types, type);
type = va_arg (args, SType *);
}
return types;
}
SType *
sformat_make_record (SFormat *format,
const char *name,
SForward *forward,
SType *content,
...)
{
SType *type;
va_list args;
GQueue *types;
GList *list;
State *begin, *state;
/* Build queue of child types */
va_start (args, content);
types = expand_varargs (content, args);
va_end (args);
/* chain types together */
state = begin = state_new (format);
for (list = types->head; list != NULL; list = list->next)
{
SType *child_type = list->data;
state_add_transition (state, child_type->enter);
state = state_new (format);
transition_set_to_state (child_type->exit, state);
}
g_queue_free (types);
/* create and return the new type */
type = type_new_from_forward (format, TYPE_RECORD, name, forward);
type->enter = transition_new (format, BEGIN, type, NULL, begin);
type->exit = transition_new (format, END, type, state, NULL);
return type;
}
SType *
sformat_make_list (SFormat *format,
const char *name,
SForward *forward,
SType *child_type)
{
SType *type;
State *list_state;
type = type_new_from_forward (format, TYPE_LIST, name, forward);
list_state = state_new (format);
type->enter = transition_new (format, BEGIN, type, NULL, list_state);
type->exit = transition_new (format, END, type, list_state, NULL);
state_add_transition (list_state, child_type->enter);
transition_set_to_state (child_type->exit, list_state);
return type;
}
SType *
sformat_make_pointer (SFormat *format,
const char *name,
SForward *forward)
{
SType *type = type_new_value (format, TYPE_POINTER, name);
type->target = (SType *)forward;
return type;
}
SType *
sformat_make_integer (SFormat *format,
const char *name)
{
return type_new_value (format, TYPE_INTEGER, name);
}
SType *
sformat_make_string (SFormat *format,
const char *name)
{
return type_new_value (format, TYPE_STRING, name);
}
gboolean
stype_is_record (SType *type)
@ -107,291 +397,6 @@ stype_get_name (SType *type)
return type->name;
}
/*
* Transition
*/
typedef enum
{
BEGIN,
VALUE,
END
} TransitionKind;
struct Transition
{
SType * type;
TransitionKind kind;
State * to;
};
static Transition *transition_new (SFormat *format,
TransitionKind kind,
SType *type,
State *from,
State *to);
static void transition_free (Transition *transition);
static void transition_set_to_state (Transition *transition,
State *to_state);
/*
* State
*/
struct State
{
GQueue *transitions;
};
static State *state_new (SFormat *format);
static void state_add_transition (State *state,
Transition *transition);
static void state_free (State *state);
/*
* Format
*/
SFormat *
sformat_new (void)
{
/* FIXME: should probably be refcounted, and an SContext
* should have a ref on the format
*/
SFormat *format = g_new0 (SFormat, 1);
format->begin = NULL;
format->end = NULL;
format->types = g_queue_new ();
format->states = g_queue_new ();
format->transitions = g_queue_new ();
return format;
}
void
sformat_free (SFormat *format)
{
GList *list;
for (list = format->types->head; list; list = list->next)
{
SType *type = list->data;
type_free (type);
}
for (list = format->states->head; list; list = list->next)
{
State *state = list->data;
state_free (state);
}
for (list = format->transitions->head; list; list = list->next)
{
Transition *transition = list->data;
transition_free (transition);
}
g_free (format);
}
void
sformat_set_type (SFormat *format,
SType *type)
{
format->begin = state_new (format);
format->end = state_new (format);
state_add_transition (format->begin, type->enter);
transition_set_to_state (type->exit, format->end);
/* Fix up pointer types */
}
/*
* Type
*/
static SType *
type_new (SFormat *format,
TypeKind kind,
const char *name)
{
SType *type = g_new0 (SType, 1);
type->kind = kind;
type->name = name? g_strdup (name) : NULL;
type->enter = NULL;
type->exit = NULL;
type->target = NULL;
g_queue_push_tail (format->types, type);
return type;
}
static void
type_free (SType *type)
{
g_free (type->name);
g_free (type);
}
static GQueue *
type_queue (SType *content1,
va_list args)
{
GQueue *types = g_queue_new ();
SType *type;
g_queue_push_tail (types, content1);
type = va_arg (args, SType *);
while (type)
{
g_queue_push_tail (types, type);
type = va_arg (args, SType *);
}
return types;
}
SForward *
sformat_declare_forward (SFormat *format)
{
SType *type = type_new (format, TYPE_FORWARD, NULL);
return (SForward *)type;
}
SType *
sformat_make_record (SFormat *format,
const char *name,
SForward *forward,
SType *content,
...)
{
SType *type;
va_list args;
GQueue *types;
GList *list;
State *begin, *state;
/* Build queue of child types */
va_start (args, content);
types = type_queue (content, args);
va_end (args);
/* chain types together */
state = begin = state_new (format);
for (list = types->head; list != NULL; list = list->next)
{
SType *child_type = list->data;
state_add_transition (state, child_type->enter);
state = state_new (format);
transition_set_to_state (child_type->exit, state);
}
g_queue_free (types);
/* Return resulting fragment */
if (forward)
{
type = (SType *)forward;
type->kind = TYPE_RECORD;
type->name = g_strdup (name);
}
else
{
type = type_new (format, TYPE_RECORD, name);
}
type->enter = transition_new (format, BEGIN, type, NULL, begin);
type->exit = transition_new (format, END, type, state, NULL);
return type;
}
SType *
sformat_make_list (SFormat *format,
const char *name,
SForward *forward,
SType *child_type)
{
SType *type;
State *list_state;
if (forward)
{
type = (SType *)forward;
type->kind = TYPE_LIST;
type->name = g_strdup (name);
}
else
{
type = type_new (format, TYPE_LIST, name);
}
list_state = state_new (format);
type->enter = transition_new (format, BEGIN, type, NULL, list_state);
type->exit = transition_new (format, END, type, list_state, NULL);
state_add_transition (list_state, child_type->enter);
transition_set_to_state (child_type->exit, list_state);
return type;
}
static SType *
type_new_value (SFormat *format, TypeKind kind, const char *name)
{
SType *type = type_new (format, kind, name);
State *before, *after;
Transition *value;
before = state_new (format);
after = state_new (format);
type->enter = transition_new (format, BEGIN, type, NULL, before);
type->exit = transition_new (format, END, type, after, NULL);
value = transition_new (format, VALUE, type, before, after);
return type;
}
SType *
sformat_make_pointer (SFormat *format,
const char *name,
SForward *forward)
{
SType *type = type_new_value (format, TYPE_POINTER, name);
type->target = (SType *)forward;
return type;
}
SType *
sformat_make_integer (SFormat *format,
const char *name)
{
return type_new_value (format, TYPE_INTEGER, name);
}
SType *
sformat_make_string (SFormat *format,
const char *name)
{
return type_new_value (format, TYPE_STRING, name);
}
/* Consider adding unions at some point
*
* To be useful they should probably be anonymous, so that
@ -414,6 +419,8 @@ sformat_make_string (SFormat *format,
* elements. That will make things a lot easier, and unions are
* still pretty useful if you put big things like lists in them.
*
* Or maybe just give them a name ...
*
* We may also consider adding anonymous records. These will
* not be able to have pointers associated with them though
* (because there wouldn't be a natural place