More work on the benchmark.

pull/13171/head
Joshua Haberman 16 years ago
parent 137991c7b2
commit 127adf4036
  1. 4
      Makefile
  2. 22
      benchmark.c
  3. 13
      upb_msg.c
  4. 2
      upb_msg.h
  5. 14
      upb_parse.c
  6. 7
      upb_parse.h

@ -3,7 +3,7 @@
CC=gcc CC=gcc
CXX=g++ CXX=g++
CFLAGS=-std=c99 CFLAGS=-std=c99
CPPFLAGS=-O0 -Wall -Wextra -pedantic -g -DUPB_UNALIGNED_READS_OK CPPFLAGS=-O3 -Wall -Wextra -pedantic -g -DUPB_UNALIGNED_READS_OK -fomit-frame-pointer
OBJ=upb_parse.o upb_table.o upb_msg.o upb_enum.o upb_context.o upb_string.o descriptor.o OBJ=upb_parse.o upb_table.o upb_msg.o upb_enum.o upb_context.o upb_string.o descriptor.o
all: $(OBJ) test_table tests upbc all: $(OBJ) test_table tests upbc
clean: clean:
@ -13,7 +13,7 @@ libupb.a: $(OBJ)
ar rcs libupb.a $(OBJ) ar rcs libupb.a $(OBJ)
test_table: libupb.a test_table: libupb.a
upbc: libupb.a upbc: libupb.a
benchmark: libupb.a benchmark: libupb.a -lm
-include deps -include deps
deps: *.c *.h deps: *.c *.h

@ -1,4 +1,5 @@
#include "test_util.h"
#include "upb_context.h" #include "upb_context.h"
#include "upb_msg.h" #include "upb_msg.h"
@ -7,7 +8,7 @@ int main ()
struct upb_context c; struct upb_context c;
upb_context_init(&c); upb_context_init(&c);
struct upb_string fds; struct upb_string fds;
if(!upb_strreadfile("google_speed.proto.bin", &fds)) { if(!upb_strreadfile("google_messages.proto.bin", &fds)) {
fprintf(stderr, "Couldn't read google_speed.proto.bin.\n"); fprintf(stderr, "Couldn't read google_speed.proto.bin.\n");
return 1; return 1;
} }
@ -34,16 +35,19 @@ int main ()
fprintf(stderr, "Error reading google_message2.dat\n"); fprintf(stderr, "Error reading google_message2.dat\n");
return 1; return 1;
} }
upb_status_t status = upb_msg_parse(&s, str.ptr, str.byte_len, &read); size_t total = 0;
for(int i = 0; i < 1000; i++) {
upb_msg_parse_reset(&s, data, m, false, true);
upb_status_t status = upb_msg_parse(&s, str.ptr, str.byte_len, &read);
if(status != UPB_STATUS_OK && read != str.byte_len) {
fprintf(stderr, "Error. :( error=%d, read=%d\n", status, read);
return 1;
}
total += str.byte_len;
}
fprintf(stderr, "Parsed %sB\n", eng(total, 3, false));
upb_msg_parse_free(&s); upb_msg_parse_free(&s);
upb_msgdata_free(data, m, true); upb_msgdata_free(data, m, true);
upb_context_free(&c); upb_context_free(&c);
upb_strfree(str); upb_strfree(str);
if(status == UPB_STATUS_OK && read == str.byte_len) {
fprintf(stderr, "Success!\n");
return 0;
} else {
fprintf(stderr, "Error. :( error=%d, read=%d\n", status, read);
return 1;
}
} }

@ -329,10 +329,10 @@ static void submsg_start_cb(struct upb_parse_state *_s, void *user_field_desc)
if(!s->merge) upb_msg_clear(frame->data, f->ref.msg); if(!s->merge) upb_msg_clear(frame->data, f->ref.msg);
} }
void upb_msg_parse_init(struct upb_msg_parse_state *s, void *msg, void upb_msg_parse_reset(struct upb_msg_parse_state *s, void *msg,
struct upb_msg *m, bool merge, bool byref) struct upb_msg *m, bool merge, bool byref)
{ {
upb_parse_init(&s->s, sizeof(struct parse_frame_data)); upb_parse_reset(&s->s);
s->merge = merge; s->merge = merge;
s->byref = byref; s->byref = byref;
if(!merge && msg == NULL) msg = upb_msgdata_new(m); if(!merge && msg == NULL) msg = upb_msgdata_new(m);
@ -343,6 +343,13 @@ void upb_msg_parse_init(struct upb_msg_parse_state *s, void *msg,
s->s.submsg_start_cb = submsg_start_cb; s->s.submsg_start_cb = submsg_start_cb;
} }
void upb_msg_parse_init(struct upb_msg_parse_state *s, void *msg,
struct upb_msg *m, bool merge, bool byref)
{
upb_parse_init(&s->s, sizeof(struct parse_frame_data));
upb_msg_parse_reset(s, msg, m, merge, byref);
}
void upb_msg_parse_free(struct upb_msg_parse_state *s) void upb_msg_parse_free(struct upb_msg_parse_state *s)
{ {
upb_parse_free(&s->s); upb_parse_free(&s->s);

@ -340,6 +340,8 @@ struct upb_msg_parse_state {
* must remain unchanged and must outlive data. */ * must remain unchanged and must outlive data. */
void upb_msg_parse_init(struct upb_msg_parse_state *s, void *data, void upb_msg_parse_init(struct upb_msg_parse_state *s, void *data,
struct upb_msg *m, bool merge, bool byref); struct upb_msg *m, bool merge, bool byref);
void upb_msg_parse_reset(struct upb_msg_parse_state *s, void *data,
struct upb_msg *m, bool merge, bool byref);
void upb_msg_parse_free(struct upb_msg_parse_state *s); void upb_msg_parse_free(struct upb_msg_parse_state *s);
/* Parses a protobuf fragment, writing the data to the message that was passed /* Parses a protobuf fragment, writing the data to the message that was passed

@ -253,17 +253,23 @@ upb_status_t upb_parse_value(void **buf, void *end, upb_field_type_t ft,
#undef CASE #undef CASE
} }
void upb_parse_init(struct upb_parse_state *state, size_t udata_size) void upb_parse_reset(struct upb_parse_state *state)
{ {
memset(state, 0, sizeof(struct upb_parse_state));
state->offset = 0; state->offset = 0;
size_t stack_bytes = (sizeof(*state->stack) + udata_size) * UPB_MAX_NESTING; state->top = state->stack;
state->stack = state->top = malloc(stack_bytes);
/* The top-level message is not delimited (we can keep receiving data for /* The top-level message is not delimited (we can keep receiving data for
* it indefinitely). */ * it indefinitely). */
state->top->end_offset = SIZE_MAX; state->top->end_offset = SIZE_MAX;
}
void upb_parse_init(struct upb_parse_state *state, size_t udata_size)
{
memset(state, 0, sizeof(struct upb_parse_state)); /* Clear all callbacks. */
size_t stack_bytes = (sizeof(*state->stack) + udata_size) * UPB_MAX_NESTING;
state->stack = malloc(stack_bytes);
state->limit = (struct upb_parse_stack_frame*)((char*)state->stack + stack_bytes); state->limit = (struct upb_parse_stack_frame*)((char*)state->stack + stack_bytes);
state->udata_size = udata_size; state->udata_size = udata_size;
upb_parse_reset(state);
} }
void upb_parse_free(struct upb_parse_state *state) void upb_parse_free(struct upb_parse_state *state)

@ -64,6 +64,7 @@ struct upb_parse_state;
* been previously allocated. udata_size specifies how much space will be * been previously allocated. udata_size specifies how much space will be
* available at parse_stack_frame.user_data in each frame for user data. */ * available at parse_stack_frame.user_data in each frame for user data. */
void upb_parse_init(struct upb_parse_state *state, size_t udata_size); void upb_parse_init(struct upb_parse_state *state, size_t udata_size);
void upb_parse_reset(struct upb_parse_state *state);
void upb_parse_free(struct upb_parse_state *state); void upb_parse_free(struct upb_parse_state *state);
/* The callback that is called immediately after a tag has been parsed. The /* The callback that is called immediately after a tag has been parsed. The
@ -140,15 +141,13 @@ INLINE bool upb_check_type(upb_wire_type_t wt, upb_field_type_t ft) {
/* Parses and converts a value from the character data starting at buf. The /* Parses and converts a value from the character data starting at buf. The
* caller must have previously checked that the wire type is appropriate for * caller must have previously checked that the wire type is appropriate for
* this field type. For delimited data, buf is advanced to the beginning of * this field type. */
* the delimited data, not the end. */
upb_status_t upb_parse_value(void **buf, void *end, upb_field_type_t ft, upb_status_t upb_parse_value(void **buf, void *end, upb_field_type_t ft,
union upb_value_ptr v); union upb_value_ptr v);
/* Parses a wire value with the given type (which must have been obtained from /* Parses a wire value with the given type (which must have been obtained from
* a tag that was just parsed) and adds the number of bytes that were consumed * a tag that was just parsed) and adds the number of bytes that were consumed
* to *offset. For delimited types, offset is advanced past the delimited * to *offset. */
* data. */
upb_status_t upb_parse_wire_value(void **buf, void *end, upb_wire_type_t wt, upb_status_t upb_parse_wire_value(void **buf, void *end, upb_wire_type_t wt,
union upb_wire_value *wv); union upb_wire_value *wv);

Loading…
Cancel
Save